From 479e9e744b7b1330f5589335fa7d0512f03c0e85 Mon Sep 17 00:00:00 2001 From: Shinpei Kato Date: Thu, 10 Nov 2011 10:36:21 -0800 Subject: [PATCH] recommit the project --- common/gdev_api.h | 62 + common/gdev_conf.h | 45 + common/gdev_ioctl_def.h | 69 + common/gdev_nvidia.c | 131 + common/gdev_nvidia.h | 327 + common/gdev_nvidia_def.h | 76 + common/gdev_time.h | 127 + driver/README | 12 + driver/configure | 32 + driver/gdev/Makefile | 5 + driver/gdev/gdev_drv.c | 238 + driver/gdev/gdev_drv.h | 119 + driver/gdev/gdev_ioctl.c | 204 + driver/gdev/gdev_ioctl.h | 41 + driver/gdev/install.sh | 41 + driver/pscnv/Makefile | 40 + driver/pscnv/configure | 13 + driver/pscnv/i2c/sil164.h | 63 + driver/pscnv/kapitest.sh | 13 + driver/pscnv/kapitest/Makefile | 23 + .../pscnv/kapitest/drm_connector_detect_1.c | 6 + .../pscnv/kapitest/drm_connector_detect_2.c | 6 + .../kapitest/drm_gem_object_handle_count.c | 6 + driver/pscnv/kapitest/drm_ioctl_def.c | 7 + driver/pscnv/kapitest/drm_ioctl_def_drv.c | 7 + driver/pscnv/kapitest/fail.c | 1 + driver/pscnv/kapitest/gamma_set_5.c | 7 + driver/pscnv/kapitest/gamma_set_6.c | 7 + driver/pscnv/kapitest/getparam_bus_type.c | 8 + driver/pscnv/kapitest/i2c_id.c | 3 + driver/pscnv/kapitest/io_mapping_2.c | 6 + driver/pscnv/kapitest/io_mapping_3.c | 6 + driver/pscnv/kapitest/map_ofs.c | 5 + driver/pscnv/kapitest/pci_driver.c | 9 + driver/pscnv/kapitest/switcheroo_reprobe.c | 8 + driver/pscnv/nouveau_acpi.c | 296 + driver/pscnv/nouveau_backlight.c | 158 + driver/pscnv/nouveau_bios.c | 6933 ++++++++ driver/pscnv/nouveau_bios.h | 335 + driver/pscnv/nouveau_calc.c | 477 + driver/pscnv/nouveau_connector.c | 945 ++ driver/pscnv/nouveau_connector.h | 61 + driver/pscnv/nouveau_crtc.h | 97 + driver/pscnv/nouveau_debugfs.c | 180 + driver/pscnv/nouveau_display.c | 106 + driver/pscnv/nouveau_dma.c | 172 + driver/pscnv/nouveau_dma.h | 166 + driver/pscnv/nouveau_dp.c | 638 + driver/pscnv/nouveau_drv.c | 533 + driver/pscnv/nouveau_drv.h | 1234 ++ driver/pscnv/nouveau_encoder.h | 103 + driver/pscnv/nouveau_fb.h | 46 + driver/pscnv/nouveau_fbcon.c | 444 + driver/pscnv/nouveau_fbcon.h | 63 + driver/pscnv/nouveau_grctx.h | 136 + driver/pscnv/nouveau_hw.c | 1086 ++ driver/pscnv/nouveau_hw.h | 455 + driver/pscnv/nouveau_i2c.c | 323 + driver/pscnv/nouveau_i2c.h | 58 + driver/pscnv/nouveau_ioc32.c | 70 + driver/pscnv/nouveau_irq.c | 1330 ++ driver/pscnv/nouveau_mem.c | 182 + driver/pscnv/nouveau_perf.c | 205 + driver/pscnv/nouveau_pm.c | 548 + driver/pscnv/nouveau_pm.h | 74 + driver/pscnv/nouveau_reg.h | 862 + driver/pscnv/nouveau_state.c | 728 + driver/pscnv/nouveau_temp.c | 309 + driver/pscnv/nouveau_volt.c | 212 + driver/pscnv/nv04_dac.c | 544 + driver/pscnv/nv04_dfp.c | 717 + driver/pscnv/nv04_pm.c | 81 + driver/pscnv/nv04_timer.c | 46 + driver/pscnv/nv04_tv.c | 254 + driver/pscnv/nv10_gpio.c | 92 + driver/pscnv/nv50_calc.c | 87 + driver/pscnv/nv50_chan.c | 180 + driver/pscnv/nv50_chan.h | 20 + driver/pscnv/nv50_crtc.c | 812 + driver/pscnv/nv50_cursor.c | 158 + driver/pscnv/nv50_dac.c | 321 + driver/pscnv/nv50_display.c | 1124 ++ driver/pscnv/nv50_display.h | 49 + driver/pscnv/nv50_evo.h | 113 + driver/pscnv/nv50_fifo.c | 460 + driver/pscnv/nv50_gpio.c | 111 + driver/pscnv/nv50_graph.c | 1006 ++ driver/pscnv/nv50_grctx.c | 3337 ++++ driver/pscnv/nv50_pm.c | 134 + driver/pscnv/nv50_sor.c | 343 + driver/pscnv/nv50_vm.c | 557 + driver/pscnv/nv50_vm.h | 31 + driver/pscnv/nv50_vram.c | 285 + driver/pscnv/nv84_crypt.c | 264 + driver/pscnv/nv98_crypt.c | 258 + driver/pscnv/nv98_crypt.fuc | 699 + driver/pscnv/nva3_copy.fuc | 872 ++ driver/pscnv/nva3_pm.c | 95 + driver/pscnv/nvc0_chan.c | 78 + driver/pscnv/nvc0_chan.h | 14 + driver/pscnv/nvc0_copy.c | 254 + driver/pscnv/nvc0_copy.fuc.h | 527 + driver/pscnv/nvc0_copy.h | 37 + driver/pscnv/nvc0_ctxctl.h | 2999 ++++ driver/pscnv/nvc0_fifo.c | 426 + driver/pscnv/nvc0_graph.c | 1138 ++ driver/pscnv/nvc0_graph.fuc | 400 + driver/pscnv/nvc0_graph.h | 79 + driver/pscnv/nvc0_grctx.c | 3009 ++++ driver/pscnv/nvc0_grgpc.fuc | 480 + driver/pscnv/nvc0_grhub.fuc | 811 + driver/pscnv/nvc0_pgraph.xml.h | 2819 ++++ driver/pscnv/nvc0_vm.c | 446 + driver/pscnv/nvc0_vm.h | 57 + driver/pscnv/nvc0_vram.c | 115 + driver/pscnv/nvreg.h | 536 + driver/pscnv/pscnv_chan.c | 235 + driver/pscnv/pscnv_chan.h | 81 + driver/pscnv/pscnv_drm.h | 173 + driver/pscnv/pscnv_engine.h | 33 + driver/pscnv/pscnv_fifo.h | 40 + driver/pscnv/pscnv_gdev.c | 377 + driver/pscnv/pscnv_gem.c | 74 + driver/pscnv/pscnv_gem.h | 37 + driver/pscnv/pscnv_ioctl.c | 500 + driver/pscnv/pscnv_ioctl.h | 36 + driver/pscnv/pscnv_kapi.h | 0 driver/pscnv/pscnv_mem.c | 192 + driver/pscnv/pscnv_mem.h | 85 + driver/pscnv/pscnv_mm.c | 321 + driver/pscnv/pscnv_mm.h | 48 + driver/pscnv/pscnv_ramht.c | 94 + driver/pscnv/pscnv_ramht.h | 41 + driver/pscnv/pscnv_sysram.c | 81 + driver/pscnv/pscnv_tree.h | 487 + driver/pscnv/pscnv_vm.c | 257 + driver/pscnv/pscnv_vm.h | 84 + runtime/configure | 38 + runtime/kernel/Makefile | 29 + runtime/kernel/gdev_lib.c | 157 + runtime/kernel/gdev_lib.h | 30 + runtime/user/gdev/Makefile | 29 + runtime/user/gdev/drm.h | 789 + runtime/user/gdev/drm_mode.h | 347 + runtime/user/gdev/gdev_lib.c | 94 + runtime/user/gdev/gdev_lib.h | 113 + runtime/user/pscnv/libpscnv.c | 193 + runtime/user/pscnv/libpscnv.h | 41 + runtime/user/pscnv/libpscnv_ib.c | 158 + runtime/user/pscnv/libpscnv_ib.h | 94 + runtime/user/pscnv/pscnv_drm.h | 157 + runtime/user/pscnv/pscnv_gdev.c | 296 + tests/common/loadstore.c | 157 + tests/common/matrixadd.c | 257 + tests/common/matrixadd.cu | 10 + tests/common/matrixadd_fermi | Bin 0 -> 1460 bytes tests/common/memcpy.c | 83 + tests/common/openclose.c | 14 + tests/cuda/matrixmul/Makefile | 13 + tests/cuda/matrixmul/main.c | 194 + tests/cuda/matrixmul/matrixmul_gpu.cubin | Bin 0 -> 2556 bytes tests/cuda/memcpy/Makefile | 13 + tests/cuda/memcpy/Makefile.pathscale | 13 + tests/cuda/memcpy/main.c | 160 + tests/cuda/memcpy/simple_example1.cubin | Bin 0 -> 1264 bytes tests/kernel/loadstore/Makefile | 38 + tests/kernel/loadstore/loadstore.c | 1 + tests/kernel/loadstore/main.c | 41 + tests/kernel/memcpy/Makefile | 38 + tests/kernel/memcpy/main.c | 65 + tests/kernel/memcpy/memcpy.c | 1 + tests/user/loadstore/Makefile | 22 + tests/user/loadstore/loadstore.c | 1 + tests/user/loadstore/main.c | 13 + tests/user/matrixadd/Makefile | 22 + tests/user/matrixadd/main.c | 33 + tests/user/matrixadd/matrixadd.c | 1 + tests/user/memcpy/Makefile | 22 + tests/user/memcpy/main.c | 76 + tests/user/memcpy/memcpy.c | 1 + tests/user/openclose/Makefile | 22 + tests/user/openclose/main.c | 12 + tests/user/openclose/main.c~ | 105 + tests/user/openclose/main.o | Bin 0 -> 1656 bytes tests/user/openclose/openclose.c | 1 + tests/user/openclose/openclose.o | Bin 0 -> 1472 bytes tests/user/openclose/user_test | Bin 0 -> 7133 bytes traces/matrix_mul_nva3_dedmaed | 5510 +++++++ traces/matrix_mul_nvc4_dedmaed | 13080 ++++++++++++++++ 189 files changed, 74473 insertions(+) create mode 100644 common/gdev_api.h create mode 100644 common/gdev_conf.h create mode 100644 common/gdev_ioctl_def.h create mode 100644 common/gdev_nvidia.c create mode 100644 common/gdev_nvidia.h create mode 100644 common/gdev_nvidia_def.h create mode 100644 common/gdev_time.h create mode 100644 driver/README create mode 100755 driver/configure create mode 100644 driver/gdev/Makefile create mode 100644 driver/gdev/gdev_drv.c create mode 100644 driver/gdev/gdev_drv.h create mode 100644 driver/gdev/gdev_ioctl.c create mode 100644 driver/gdev/gdev_ioctl.h create mode 100644 driver/gdev/install.sh create mode 100644 driver/pscnv/Makefile create mode 100755 driver/pscnv/configure create mode 100644 driver/pscnv/i2c/sil164.h create mode 100755 driver/pscnv/kapitest.sh create mode 100644 driver/pscnv/kapitest/Makefile create mode 100644 driver/pscnv/kapitest/drm_connector_detect_1.c create mode 100644 driver/pscnv/kapitest/drm_connector_detect_2.c create mode 100644 driver/pscnv/kapitest/drm_gem_object_handle_count.c create mode 100644 driver/pscnv/kapitest/drm_ioctl_def.c create mode 100644 driver/pscnv/kapitest/drm_ioctl_def_drv.c create mode 100644 driver/pscnv/kapitest/fail.c create mode 100644 driver/pscnv/kapitest/gamma_set_5.c create mode 100644 driver/pscnv/kapitest/gamma_set_6.c create mode 100644 driver/pscnv/kapitest/getparam_bus_type.c create mode 100644 driver/pscnv/kapitest/i2c_id.c create mode 100644 driver/pscnv/kapitest/io_mapping_2.c create mode 100644 driver/pscnv/kapitest/io_mapping_3.c create mode 100644 driver/pscnv/kapitest/map_ofs.c create mode 100644 driver/pscnv/kapitest/pci_driver.c create mode 100644 driver/pscnv/kapitest/switcheroo_reprobe.c create mode 100644 driver/pscnv/nouveau_acpi.c create mode 100644 driver/pscnv/nouveau_backlight.c create mode 100644 driver/pscnv/nouveau_bios.c create mode 100644 driver/pscnv/nouveau_bios.h create mode 100644 driver/pscnv/nouveau_calc.c create mode 100644 driver/pscnv/nouveau_connector.c create mode 100644 driver/pscnv/nouveau_connector.h create mode 100644 driver/pscnv/nouveau_crtc.h create mode 100644 driver/pscnv/nouveau_debugfs.c create mode 100644 driver/pscnv/nouveau_display.c create mode 100644 driver/pscnv/nouveau_dma.c create mode 100644 driver/pscnv/nouveau_dma.h create mode 100644 driver/pscnv/nouveau_dp.c create mode 100644 driver/pscnv/nouveau_drv.c create mode 100644 driver/pscnv/nouveau_drv.h create mode 100644 driver/pscnv/nouveau_encoder.h create mode 100644 driver/pscnv/nouveau_fb.h create mode 100644 driver/pscnv/nouveau_fbcon.c create mode 100644 driver/pscnv/nouveau_fbcon.h create mode 100644 driver/pscnv/nouveau_grctx.h create mode 100644 driver/pscnv/nouveau_hw.c create mode 100644 driver/pscnv/nouveau_hw.h create mode 100644 driver/pscnv/nouveau_i2c.c create mode 100644 driver/pscnv/nouveau_i2c.h create mode 100644 driver/pscnv/nouveau_ioc32.c create mode 100644 driver/pscnv/nouveau_irq.c create mode 100644 driver/pscnv/nouveau_mem.c create mode 100644 driver/pscnv/nouveau_perf.c create mode 100644 driver/pscnv/nouveau_pm.c create mode 100644 driver/pscnv/nouveau_pm.h create mode 100644 driver/pscnv/nouveau_reg.h create mode 100644 driver/pscnv/nouveau_state.c create mode 100644 driver/pscnv/nouveau_temp.c create mode 100644 driver/pscnv/nouveau_volt.c create mode 100644 driver/pscnv/nv04_dac.c create mode 100644 driver/pscnv/nv04_dfp.c create mode 100644 driver/pscnv/nv04_pm.c create mode 100644 driver/pscnv/nv04_timer.c create mode 100644 driver/pscnv/nv04_tv.c create mode 100644 driver/pscnv/nv10_gpio.c create mode 100644 driver/pscnv/nv50_calc.c create mode 100644 driver/pscnv/nv50_chan.c create mode 100644 driver/pscnv/nv50_chan.h create mode 100644 driver/pscnv/nv50_crtc.c create mode 100644 driver/pscnv/nv50_cursor.c create mode 100644 driver/pscnv/nv50_dac.c create mode 100644 driver/pscnv/nv50_display.c create mode 100644 driver/pscnv/nv50_display.h create mode 100644 driver/pscnv/nv50_evo.h create mode 100644 driver/pscnv/nv50_fifo.c create mode 100644 driver/pscnv/nv50_gpio.c create mode 100644 driver/pscnv/nv50_graph.c create mode 100644 driver/pscnv/nv50_grctx.c create mode 100644 driver/pscnv/nv50_pm.c create mode 100644 driver/pscnv/nv50_sor.c create mode 100644 driver/pscnv/nv50_vm.c create mode 100644 driver/pscnv/nv50_vm.h create mode 100644 driver/pscnv/nv50_vram.c create mode 100644 driver/pscnv/nv84_crypt.c create mode 100644 driver/pscnv/nv98_crypt.c create mode 100644 driver/pscnv/nv98_crypt.fuc create mode 100644 driver/pscnv/nva3_copy.fuc create mode 100644 driver/pscnv/nva3_pm.c create mode 100644 driver/pscnv/nvc0_chan.c create mode 100644 driver/pscnv/nvc0_chan.h create mode 100644 driver/pscnv/nvc0_copy.c create mode 100644 driver/pscnv/nvc0_copy.fuc.h create mode 100644 driver/pscnv/nvc0_copy.h create mode 100644 driver/pscnv/nvc0_ctxctl.h create mode 100644 driver/pscnv/nvc0_fifo.c create mode 100644 driver/pscnv/nvc0_graph.c create mode 100644 driver/pscnv/nvc0_graph.fuc create mode 100644 driver/pscnv/nvc0_graph.h create mode 100644 driver/pscnv/nvc0_grctx.c create mode 100644 driver/pscnv/nvc0_grgpc.fuc create mode 100644 driver/pscnv/nvc0_grhub.fuc create mode 100644 driver/pscnv/nvc0_pgraph.xml.h create mode 100644 driver/pscnv/nvc0_vm.c create mode 100644 driver/pscnv/nvc0_vm.h create mode 100644 driver/pscnv/nvc0_vram.c create mode 100644 driver/pscnv/nvreg.h create mode 100644 driver/pscnv/pscnv_chan.c create mode 100644 driver/pscnv/pscnv_chan.h create mode 100644 driver/pscnv/pscnv_drm.h create mode 100644 driver/pscnv/pscnv_engine.h create mode 100644 driver/pscnv/pscnv_fifo.h create mode 100644 driver/pscnv/pscnv_gdev.c create mode 100644 driver/pscnv/pscnv_gem.c create mode 100644 driver/pscnv/pscnv_gem.h create mode 100644 driver/pscnv/pscnv_ioctl.c create mode 100644 driver/pscnv/pscnv_ioctl.h create mode 100644 driver/pscnv/pscnv_kapi.h create mode 100644 driver/pscnv/pscnv_mem.c create mode 100644 driver/pscnv/pscnv_mem.h create mode 100644 driver/pscnv/pscnv_mm.c create mode 100644 driver/pscnv/pscnv_mm.h create mode 100644 driver/pscnv/pscnv_ramht.c create mode 100644 driver/pscnv/pscnv_ramht.h create mode 100644 driver/pscnv/pscnv_sysram.c create mode 100644 driver/pscnv/pscnv_tree.h create mode 100644 driver/pscnv/pscnv_vm.c create mode 100644 driver/pscnv/pscnv_vm.h create mode 100755 runtime/configure create mode 100644 runtime/kernel/Makefile create mode 100644 runtime/kernel/gdev_lib.c create mode 100644 runtime/kernel/gdev_lib.h create mode 100644 runtime/user/gdev/Makefile create mode 100644 runtime/user/gdev/drm.h create mode 100644 runtime/user/gdev/drm_mode.h create mode 100644 runtime/user/gdev/gdev_lib.c create mode 100644 runtime/user/gdev/gdev_lib.h create mode 100644 runtime/user/pscnv/libpscnv.c create mode 100644 runtime/user/pscnv/libpscnv.h create mode 100644 runtime/user/pscnv/libpscnv_ib.c create mode 100644 runtime/user/pscnv/libpscnv_ib.h create mode 100644 runtime/user/pscnv/pscnv_drm.h create mode 100644 runtime/user/pscnv/pscnv_gdev.c create mode 100644 tests/common/loadstore.c create mode 100644 tests/common/matrixadd.c create mode 100644 tests/common/matrixadd.cu create mode 100644 tests/common/matrixadd_fermi create mode 100644 tests/common/memcpy.c create mode 100644 tests/common/openclose.c create mode 100644 tests/cuda/matrixmul/Makefile create mode 100644 tests/cuda/matrixmul/main.c create mode 100644 tests/cuda/matrixmul/matrixmul_gpu.cubin create mode 100644 tests/cuda/memcpy/Makefile create mode 100644 tests/cuda/memcpy/Makefile.pathscale create mode 100644 tests/cuda/memcpy/main.c create mode 100644 tests/cuda/memcpy/simple_example1.cubin create mode 100644 tests/kernel/loadstore/Makefile create mode 120000 tests/kernel/loadstore/loadstore.c create mode 100644 tests/kernel/loadstore/main.c create mode 100644 tests/kernel/memcpy/Makefile create mode 100644 tests/kernel/memcpy/main.c create mode 120000 tests/kernel/memcpy/memcpy.c create mode 100644 tests/user/loadstore/Makefile create mode 120000 tests/user/loadstore/loadstore.c create mode 100644 tests/user/loadstore/main.c create mode 100644 tests/user/matrixadd/Makefile create mode 100644 tests/user/matrixadd/main.c create mode 120000 tests/user/matrixadd/matrixadd.c create mode 100644 tests/user/memcpy/Makefile create mode 100644 tests/user/memcpy/main.c create mode 120000 tests/user/memcpy/memcpy.c create mode 100644 tests/user/openclose/Makefile create mode 100644 tests/user/openclose/main.c create mode 100644 tests/user/openclose/main.c~ create mode 100644 tests/user/openclose/main.o create mode 120000 tests/user/openclose/openclose.c create mode 100644 tests/user/openclose/openclose.o create mode 100755 tests/user/openclose/user_test create mode 100644 traces/matrix_mul_nva3_dedmaed create mode 100644 traces/matrix_mul_nvc4_dedmaed diff --git a/common/gdev_api.h b/common/gdev_api.h new file mode 100644 index 00000000..96d64403 --- /dev/null +++ b/common/gdev_api.h @@ -0,0 +1,62 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __GDEV_API_H__ +#define __GDEV_API_H__ + +#ifdef __KERNEL__ +#include "gdev_drv.h" +#else +#include "gdev_lib.h" +#endif +#include "gdev_nvidia_def.h" +/* add also: + * #include "gdev_amd_def.h" + * #include "gdev_intel_def.h" + */ + +/** + * Gdev APIs: + */ +extern gdev_handle_t *gopen(int); +extern int gclose(gdev_handle_t*); +extern uint64_t gmalloc(gdev_handle_t*, uint64_t); +extern void gfree(gdev_handle_t*, uint64_t); +extern int gmemcpy_from_device(gdev_handle_t*, void*, uint64_t, uint64_t); +extern int gmemcpy_user_from_device(gdev_handle_t*, void*, uint64_t, uint64_t); +extern int gmemcpy_to_device(gdev_handle_t*, uint64_t, void*, uint64_t); +extern int gmemcpy_user_to_device(gdev_handle_t*, uint64_t, void*, uint64_t); +extern int gmemcpy_in_device(gdev_handle_t*, uint64_t, uint64_t, uint64_t); +extern int glaunch(gdev_handle_t*, struct gdev_kernel*, uint32_t*); +extern void gsync(gdev_handle_t*, uint32_t); +extern int gquery(gdev_handle_t*, uint32_t, uint32_t*); +extern int gtune(gdev_handle_t*, uint32_t, uint32_t); + +/** + * tuning types for Gdev resource management parameters. + */ +#define GDEV_TUNE_MEMCPY_PIPELINE_COUNT 1 +#define GDEV_TUNE_MEMCPY_CHUNK_SIZE 2 + +#endif diff --git a/common/gdev_conf.h b/common/gdev_conf.h new file mode 100644 index 00000000..9a0dac25 --- /dev/null +++ b/common/gdev_conf.h @@ -0,0 +1,45 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __GDEV_CONF_H__ +#define __GDEV_CONF_H__ + +#include "gdev_nvidia.h" +// #include "gdev_amd.h" +// #include "gdev_intel.h" + +#define GDEV_PIPELINE_MAX_COUNT 8 +#define GDEV_PIPELINE_MIN_COUNT 1 +#define GDEV_PIPELINE_DEFAULT_COUNT 1 + +#define GDEV_CHUNK_MAX_SIZE 0x2000000 /* 32MB */ +#define GDEV_CHUNK_DEFAULT_SIZE 0x100000 /* 1MB */ + +/* define this if you want to allocate a new bounce buffer every time + you copy data to/from device memory. */ +//#define GDEV_NO_STATIC_BOUNCE_BUFFER + +#define GDEV_DEBUG_PRINT 0 + +#endif diff --git a/common/gdev_ioctl_def.h b/common/gdev_ioctl_def.h new file mode 100644 index 00000000..13b697f9 --- /dev/null +++ b/common/gdev_ioctl_def.h @@ -0,0 +1,69 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __GDEV_IOCTL_DEF_H__ +#define __GDEV_IOCTL_DEF_H__ + +/** + * user-space ioctl commands: + */ +#define GDEV_IOCTL_GMALLOC 0x100 +#define GDEV_IOCTL_GFREE 0x101 +#define GDEV_IOCTL_GMEMCPY_FROM_DEVICE 0x102 +#define GDEV_IOCTL_GMEMCPY_TO_DEVICE 0x103 +#define GDEV_IOCTL_GMEMCPY_IN_DEVICE 0x104 +#define GDEV_IOCTL_GLAUNCH 0x105 +#define GDEV_IOCTL_GSYNC 0x106 +#define GDEV_IOCTL_GQUERY 0x107 +#define GDEV_IOCTL_GTUNE 0x108 + +typedef struct gdev_ioctl_mem { + uint64_t addr; + uint64_t size; +} gdev_ioctl_mem_t; + +typedef struct gdev_ioctl_dma { + void *src_buf; + void *dst_buf; + uint64_t src_addr; + uint64_t dst_addr; + uint64_t size; +} gdev_ioctl_dma_t; + +typedef struct gdev_ioctl_launch { + struct gdev_kernel *kernel; + uint32_t *id; +} gdev_ioctl_launch_t; + +typedef struct gdev_ioctl_query { + uint32_t type; + uint32_t result; +} gdev_ioctl_query_t; + +typedef struct gdev_ioctl_tune { + uint32_t type; + uint32_t value; +} gdev_ioctl_tune_t; + +#endif diff --git a/common/gdev_nvidia.c b/common/gdev_nvidia.c new file mode 100644 index 00000000..8ef55816 --- /dev/null +++ b/common/gdev_nvidia.c @@ -0,0 +1,131 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "gdev_nvidia.h" + +/* add the device memory object to the memory list. */ +void gdev_heap_add(gdev_mem_t *mem) +{ + gdev_vas_t *vas = mem->vas; + + __gdev_list_add(&mem->list_entry, &vas->memlist); +} + +/* delete the device memory object from the memory list. */ +void gdev_heap_del(gdev_mem_t *mem) +{ + __gdev_list_del(&mem->list_entry); +} + +/* look up the memory object allocated at the specified address. */ +gdev_mem_t *gdev_heap_lookup(gdev_vas_t *vas, uint64_t addr) +{ + gdev_mem_t *mem; + gdev_list_t *entry = vas->memlist.next; + + while (entry) { + mem = (gdev_mem_t *)entry->container; + if (mem && mem->addr == addr) + return mem; + entry = entry->next; + } + + return NULL; +} + +/* copy data of @size from @src_addr to @dst_addr. */ +uint32_t gdev_memcpy +(gdev_ctx_t *ctx, uint64_t dst_addr, uint64_t src_addr, uint32_t size) +{ + gdev_vas_t *vas = ctx->vas; + gdev_device_t *gdev = vas->gdev; + struct gdev_compute *compute = gdev->compute; + uint32_t sequence = ++ctx->fence.sequence[GDEV_FENCE_DMA]; + + /* it's important to emit a fence *before* memcpy(): + the EXEC method of the PCOPY and M2MF engines is associated with + the QUERY method, i.e., if QUERY is set, the sequence will be + written to the specified address when the data are transfered. */ + compute->fence_write(ctx, GDEV_FENCE_DMA, sequence); + compute->memcpy(ctx, dst_addr, src_addr, size); + + return sequence; +} + +/* launch the kernel onto the GPU. */ +uint32_t gdev_launch(gdev_ctx_t *ctx, struct gdev_kernel *kern) +{ + gdev_vas_t *vas = ctx->vas; + gdev_device_t *gdev = vas->gdev; + struct gdev_compute *compute = gdev->compute; + uint32_t sequence = ++ctx->fence.sequence[GDEV_FENCE_COMPUTE]; + + /* it's important to emit a fence *after* launch(): + the LAUNCH method of the PGRAPH engine is not associated with + the QUERY method, i.e., we have to submit the QUERY method + explicitly after the kernel is launched. */ + compute->launch(ctx, kern); + compute->fence_write(ctx, GDEV_FENCE_COMPUTE, sequence); + + return sequence; +} + +/* barrier memory access. */ +void gdev_mb(gdev_ctx_t *ctx) +{ + gdev_vas_t *vas = ctx->vas; + gdev_device_t *gdev = vas->gdev; + struct gdev_compute *compute = gdev->compute; + + compute->membar(ctx); +} + +/* poll until the resource becomes available. */ +void gdev_poll(gdev_ctx_t *ctx, int type, uint32_t sequence) +{ + gdev_vas_t *vas = ctx->vas; + gdev_device_t *gdev = vas->gdev; + struct gdev_compute *compute = gdev->compute; + uint32_t poll_times = 0; + uint32_t val; + + compute->fence_read(ctx, type, &val); + + while (val < sequence || val > sequence + GDEV_FENCE_LIMIT) { + /* relax the polling after some time. */ + if (poll_times > 0x80000000) { + SCHED_YIELD(); + } + else if (poll_times == 0xffffffff) { + poll_times = 0; + } + poll_times++; + compute->fence_read(ctx, type, &val); + } + + /* sequence rolls back to zero, if necessary. */ + if (ctx->fence.sequence[type] == GDEV_FENCE_LIMIT) { + ctx->fence.sequence[type] = 0; + } +} diff --git a/common/gdev_nvidia.h b/common/gdev_nvidia.h new file mode 100644 index 00000000..7511c27d --- /dev/null +++ b/common/gdev_nvidia.h @@ -0,0 +1,327 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __GDEV_NVIDIA_H__ +#define __GDEV_NVIDIA_H__ + +#ifdef __KERNEL__ +#include "gdev_drv.h" +#else +#include "gdev_lib.h" +#endif +#include "gdev_nvidia_def.h" + +//#define GDEV_DMA_PCOPY + +#define GDEV_SUBCH_COMPUTE 1 +#define GDEV_SUBCH_M2MF 2 +#define GDEV_SUBCH_PCOPY0 3 +#define GDEV_SUBCH_PCOPY1 4 + +#define GDEV_FENCE_COUNT 4 /* the number of fence types. */ +#define GDEV_FENCE_COMPUTE 0 +#define GDEV_FENCE_M2MF 1 +#define GDEV_FENCE_PCOPY0 2 +#define GDEV_FENCE_PCOPY1 3 +#ifdef GDEV_DMA_PCOPY +#define GDEV_FENCE_DMA GDEV_FENCE_PCOPY0 +#else +#define GDEV_FENCE_DMA GDEV_FENCE_M2MF +#endif + +#define GDEV_FENCE_LIMIT 0x80000000 + +/** + * virutal address space available for user buffers. + */ +#define GDEV_VAS_USER_START 0x20000000 +#define GDEV_VAS_USER_END (1ull << 40) +#define GDEV_VAS_SIZE GDEV_VAS_USER_END + +/* a list structure: we could use Linux's list_head, but it's not available + in user-space - hence use our own list structure. */ +struct gdev_list_head { + struct gdev_list_head *next; + struct gdev_list_head *prev; + void *container; +}; + +/** + * virtual address space (VAS) object struct: + * + * NVIDIA GPUs support virtual memory (VM) with 40 bits addressing. + * VAS hence ranges in [0:1<<40]. In particular, the pscnv bo function will + * allocate [0x20000000:1<<40] to any buffers in so called global memory, + * local memory, and constant memory. the rest of VAS is used for different + * purposes, e.g., for shared memory. + * CUDA programs access these memory spaces as follows: + * g[$reg] redirects to one of g[$reg], l[$reg-$lbase], and s[$reg-$sbase], + * depending on how local memory and shared memory are set up. + * in other words, g[$reg] may reference global memory, local memory, and + * shared memory. + * $lbase and $sbase are respectively local memory and shared memory base + * addresses, which are configured when GPU kernels are launched. + * l[0] and g[$lbase] reference the same address, so do s[0] and g[$sbase]. + * constant memory, c[], is another type of memory space that is often used + * to store GPU kernels' parameters (arguments). + * global memory, local memory, and constant memory are usually mapped on + * device memory, a.k.a., video RAM (VRAM), though they could also be mapped + * on host memory, a.k.a., system RAM (SysRAM), while shared memory is always + * mapped on SRAM present in each MP. + */ +struct gdev_vas { + void *pvas; /* driver private object. */ + gdev_device_t *gdev; /* vas is associated with a specific device. */ + gdev_list_t memlist; /* list of memory allocated */ +}; + +/** + * GPU context object struct: + */ +struct gdev_ctx { + void *pctx; /* driver private object. */ + gdev_vas_t *vas; /* chan is associated with a specific vas object. */ + struct gdev_fifo { + volatile uint32_t *regs; /* channel control registers. */ + void *ib_bo; /* driver private object. */ + uint32_t *ib_map; + uint32_t ib_order; + uint64_t ib_base; + uint32_t ib_mask; + uint32_t ib_put; + uint32_t ib_get; + void *pb_bo; /* driver private object. */ + uint32_t *pb_map; + uint32_t pb_order; + uint64_t pb_base; + uint32_t pb_mask; + uint32_t pb_size; + uint32_t pb_pos; + uint32_t pb_put; + uint32_t pb_get; + } fifo; /* command FIFO queue struct. */ + struct gdev_fence { /* fence objects (for compute and dma). */ + void *bo; /* driver private object. */ + uint32_t *map; + uint64_t addr; + uint32_t sequence[GDEV_FENCE_COUNT]; + } fence; +}; + +/** + * device/host memory object struct: + */ +struct gdev_mem { + void *bo; /* driver private object. */ + gdev_vas_t *vas; /* mem is associated with a specific vas object. */ + gdev_list_t list_entry; /* entry to the memory list. */ + uint64_t addr; /* virtual memory address. */ + void *map; /* memory-mapped buffer (for host only). */ +}; + +/* private compute functions. */ +struct gdev_compute { + void (*launch)(gdev_ctx_t*, struct gdev_kernel*); + void (*fence_write)(gdev_ctx_t*, int, uint32_t); + void (*fence_read)(gdev_ctx_t*, int, uint32_t*); + void (*memcpy)(gdev_ctx_t*, uint64_t, uint64_t, uint32_t); + void (*membar)(gdev_ctx_t*); + void (*init)(gdev_ctx_t*); +}; + +/** + * utility macros + */ +#define GDEV_MEM_ADDR(mem) (mem)->addr +#define GDEV_MEM_BUF(mem) (mem)->map + +/** + * runtime/driver-dependent resource management functions. + */ +int gdev_compute_init(gdev_device_t*); +int gdev_info_query(gdev_device_t*, uint32_t, uint32_t*); +gdev_device_t *gdev_dev_open(int); +void gdev_dev_close(gdev_device_t*); +gdev_vas_t *gdev_vas_new(gdev_device_t*, uint64_t); +void gdev_vas_free(gdev_vas_t*); +gdev_ctx_t *gdev_ctx_new(gdev_device_t*, gdev_vas_t*); +void gdev_ctx_free(gdev_ctx_t*); +gdev_mem_t *gdev_malloc_device(gdev_vas_t*, uint64_t); +void gdev_free_device(gdev_mem_t*); +gdev_mem_t *gdev_malloc_dma(gdev_vas_t*, uint64_t); +void gdev_free_dma(gdev_mem_t*); + +/** + * architecture-dependent setup functions. + */ +void nvc0_compute_setup(gdev_device_t *gdev); + + +/** + * runtime/driver/architecture-independent compute functions. + */ +uint32_t gdev_memcpy(gdev_ctx_t*, uint64_t, uint64_t, uint32_t); +uint32_t gdev_launch(gdev_ctx_t*, struct gdev_kernel*); +void gdev_mb(gdev_ctx_t*); +void gdev_poll(gdev_ctx_t*, int, uint32_t); + +/** + * runtime/driver/architecture-independent heap operations. + */ +void gdev_heap_add(gdev_mem_t*); +void gdev_heap_del(gdev_mem_t*); +gdev_mem_t *gdev_heap_lookup(gdev_vas_t*, uint64_t); + +/** + * runtime/driver/architecture-independent inline FIFO functions. + */ +static inline void __gdev_relax_fifo(void) +{ + SCHED_YIELD(); +} + +static inline void __gdev_push_fifo +(gdev_ctx_t *ctx, uint64_t base, uint32_t len, int flags) +{ + uint64_t w = base | (uint64_t)len << 40 | (uint64_t)flags << 40; + while (((ctx->fifo.ib_put + 1) & ctx->fifo.ib_mask) == ctx->fifo.ib_get) { + uint32_t old = ctx->fifo.ib_get; + ctx->fifo.ib_get = ctx->fifo.regs[0x88/4]; + if (old == ctx->fifo.ib_get) { + __gdev_relax_fifo(); + } + } + ctx->fifo.ib_map[ctx->fifo.ib_put * 2] = w; + ctx->fifo.ib_map[ctx->fifo.ib_put * 2 + 1] = w >> 32; + ctx->fifo.ib_put++; + ctx->fifo.ib_put &= ctx->fifo.ib_mask; + MB(); /* is this needed? */ + ctx->fifo.ib_map[0] = ctx->fifo.ib_map[0]; /* flush writes? */ + ctx->fifo.regs[0x8c/4] = ctx->fifo.ib_put; +} + +static inline void __gdev_update_get(gdev_ctx_t *ctx) +{ + uint32_t lo = ctx->fifo.regs[0x58/4]; + uint32_t hi = ctx->fifo.regs[0x5c/4]; + if (hi & 0x80000000) { + uint64_t mg = ((uint64_t)hi << 32 | lo) & 0xffffffffffull; + ctx->fifo.pb_get = mg - ctx->fifo.pb_base; + } else { + ctx->fifo.pb_get = 0; + } +} + +static inline void __gdev_fire_ring(gdev_ctx_t *ctx) +{ + if (ctx->fifo.pb_pos != ctx->fifo.pb_put) { + if (ctx->fifo.pb_pos > ctx->fifo.pb_put) { + uint64_t base = ctx->fifo.pb_base + ctx->fifo.pb_put; + uint32_t len = ctx->fifo.pb_pos - ctx->fifo.pb_put; + __gdev_push_fifo(ctx, base, len, 0); + } + else { + uint64_t base = ctx->fifo.pb_base + ctx->fifo.pb_put; + uint32_t len = ctx->fifo.pb_size - ctx->fifo.pb_put; + __gdev_push_fifo(ctx, base, len, 0); + /* why need this? */ + if (ctx->fifo.pb_pos) { + __gdev_push_fifo(ctx, ctx->fifo.pb_base, ctx->fifo.pb_pos, 0); + } + } + ctx->fifo.pb_put = ctx->fifo.pb_pos; + } +} + +static inline void __gdev_out_ring(gdev_ctx_t *ctx, uint32_t word) +{ + while (((ctx->fifo.pb_pos + 4) & ctx->fifo.pb_mask) == ctx->fifo.pb_get) { + uint32_t old = ctx->fifo.pb_get; + __gdev_fire_ring(ctx); + __gdev_update_get(ctx); + if (old == ctx->fifo.pb_get) { + __gdev_relax_fifo(); + } + } + ctx->fifo.pb_map[ctx->fifo.pb_pos/4] = word; + ctx->fifo.pb_pos += 4; + ctx->fifo.pb_pos &= ctx->fifo.pb_mask; +} + +static inline void __gdev_begin_ring_nv50 +(gdev_ctx_t *ctx, int subc, int mthd, int len) +{ + __gdev_out_ring(ctx, mthd | (subc<<13) | (len<<18)); +} + +static inline void __gdev_begin_ring_nv50_const +(gdev_ctx_t *ctx, int subc, int mthd, int len) +{ + __gdev_out_ring(ctx, mthd | (subc<<13) | (len<<18) | (0x4<<28)); +} + +static inline void __gdev_begin_ring_nvc0 +(gdev_ctx_t *ctx, int subc, int mthd, int len) +{ + __gdev_out_ring(ctx, (0x2<<28) | (len<<16) | (subc<<13) | (mthd>>2)); +} + +static inline void __gdev_begin_ring_nvc0_const +(gdev_ctx_t *ctx, int subc, int mthd, int len) +{ + __gdev_out_ring(ctx, (0x6<<28) | (len<<16) | (subc<<13) | (mthd>>2)); +} + +static inline void __gdev_list_init(gdev_list_t *entry, void *container) +{ + entry->next = entry->prev = NULL; + entry->container = container; +} + +static inline void __gdev_list_add(gdev_list_t *entry, gdev_list_t *head) +{ + gdev_list_t *next = head->next; + + entry->next = next; + if (next) + next->prev = entry; + entry->prev = NULL; /* don't link to the head. */ + head->next = entry; +} + +static inline void __gdev_list_del(gdev_list_t *entry) +{ + gdev_list_t *next = entry->next; + gdev_list_t *prev = entry->prev; + + if (next) { + next->prev = entry->prev; + } + if (prev) { + prev->next = entry->next; + } + entry->next = entry->prev = NULL; +} + +#endif diff --git a/common/gdev_nvidia_def.h b/common/gdev_nvidia_def.h new file mode 100644 index 00000000..315a1569 --- /dev/null +++ b/common/gdev_nvidia_def.h @@ -0,0 +1,76 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __GDEV_NVIDIA_DEF_H__ +#define __GDEV_NVIDIA_DEF_H__ + +#ifdef __KERNEL__ +#include +#else +#include +#endif + +/** + * query values for the device-specific information + */ +#define GDEV_QUERY_NVIDIA_MP_COUNT 100 + +/** + * GPGPU kernel object struct: + * we use the same kernel struct between user-space and kernel-space. + * + * if you want to know how NVIDIA GPGPU kernels work, please reference + * the NVIDIA docs and/or the PSCNV wiki available at: + * https://github.com/pathscale/pscnv/wiki/Nvidia_Compute + */ +struct gdev_kernel { + uint64_t code_addr; /* code address in VAS */ + uint32_t code_pc; /* initial program counter */ + uint64_t cmem_addr; /* constant memory address in VAS */ + uint32_t cmem_segment; /* constant segment index */ + uint32_t cmem_size; /* constant memory size */ + uint64_t lmem_addr; /* local memory address in VAS */ + uint64_t lmem_size_total; /* local memory size for all threads */ + uint32_t lmem_size; /* local memory size per thread (l[positive]) */ + uint32_t lmem_size_neg; /* local memory size per thread (l[negaive]) */ + uint32_t lmem_base; /* $lbase */ + uint32_t smem_size; /* shared memory size */ + uint32_t smem_base; /* $sbase */ + uint32_t param_start; /* parameter start position (compiler-dependent) */ + uint32_t param_count; /* parameter count */ + uint32_t *param_buf; /* parameter data */ + uint32_t stack_level; /* stack level */ + uint32_t warp_size; /* warp size */ + uint32_t reg_count; /* register count */ + uint32_t bar_count; /* barrier count */ + uint32_t grid_id; /* grid ID */ + uint32_t grid_x; /* grid dimension X */ + uint32_t grid_y; /* grid dimension Y */ + uint32_t grid_z; /* grid dimension Z */ + uint32_t block_x; /* block dimension X */ + uint32_t block_y; /* block dimension Y */ + uint32_t block_z; /* block dimension Z */ +}; + +#endif diff --git a/common/gdev_time.h b/common/gdev_time.h new file mode 100644 index 00000000..6ff55694 --- /dev/null +++ b/common/gdev_time.h @@ -0,0 +1,127 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __GDEV_TIME_H__ +#define __GDEV_TIME_H__ + +#ifdef __KERNEL__ +#define gettimeofday(x, y) do_gettimeofday(x) +#include +#else +#include +#endif + +#define USEC_1SEC 1000000 +#define USEC_1MSEC 1000 +#define MSEC_1SEC 1000 + +typedef struct timeval gdev_time_t; + +/* ret = current time. */ +static inline void gdev_time_stamp(gdev_time_t *ret) +{ + gettimeofday(ret, NULL); +} + +/* ret = x + y. */ +static inline void gdev_time_add +(gdev_time_t *ret, gdev_time_t *x, gdev_time_t *y) +{ + ret->tv_sec = x->tv_sec + y->tv_sec; + ret->tv_usec = x->tv_usec + y->tv_usec; + if (ret->tv_usec >= USEC_1SEC) { + ret->tv_sec++; + ret->tv_usec -= USEC_1SEC; + } +} + +/* ret = x - y. */ +static inline void gdev_time_sub +(gdev_time_t *ret, gdev_time_t *x, gdev_time_t *y) +{ + ret->tv_sec = x->tv_sec - y->tv_sec; + ret->tv_usec = x->tv_usec - y->tv_usec; + if (ret->tv_usec < 0) { + ret->tv_sec--; + ret->tv_usec += USEC_1SEC; + } +} + +/* ret = x * I. */ +static inline void gdev_time_mul(gdev_time_t *ret, gdev_time_t *x, int I) +{ + ret->tv_sec = x->tv_sec * I; + ret->tv_usec = x->tv_usec * I; + if (ret->tv_usec >= USEC_1SEC) { + unsigned long carry = ret->tv_usec / USEC_1SEC; + ret->tv_sec += carry; + ret->tv_usec -= carry * USEC_1SEC; + } +} + +/* ret = x / I. */ +static inline void gdev_time_div(gdev_time_t *ret, gdev_time_t *x, int I) +{ + ret->tv_sec = x->tv_sec / I; + ret->tv_usec = x->tv_usec / I; +} + +/* x >= y. */ +static inline int gdev_time_ge(gdev_time_t *x, gdev_time_t *y) +{ + return x->tv_sec == y->tv_sec ? + x->tv_usec >= y->tv_usec : + x->tv_sec >= y->tv_sec; +} + +/* tvge: x <= y. */ +static inline int gdev_time_le(gdev_time_t *x, gdev_time_t *y) +{ + return x->tv_sec == y->tv_sec ? + x->tv_usec <= y->tv_usec : + x->tv_sec <= y->tv_sec; +} + +/* generate timeval from msecs. */ +static inline void gdev_time_ms(gdev_time_t *ret, unsigned long ms) +{ + unsigned long carry = ms / MSEC_1SEC; + ret->tv_sec = carry; + ret->tv_usec = (ms - carry * MSEC_1SEC) * USEC_1MSEC; +} + +/* generate timeval from usecs. */ +static inline void gdev_time_us(gdev_time_t *ret, unsigned long us) +{ + ret->tv_sec = 0; + ret->tv_usec = us; +} + +/* clear the timeval values. */ +static inline void gdev_time_clear(gdev_time_t *tv) +{ + tv->tv_sec = tv->tv_usec = 0; +} + +#endif diff --git a/driver/README b/driver/README new file mode 100644 index 00000000..732b8a10 --- /dev/null +++ b/driver/README @@ -0,0 +1,12 @@ +To build the kernel module: + +$ mkdir build +$ cd build +$ ../configure --driver=pscnv # or --driver=nouveau +$ make +$ sudo init 3 +$ sudo make install + +To clean the kernel module build: + +$ rm -fr build diff --git a/driver/configure b/driver/configure new file mode 100755 index 00000000..9e71b740 --- /dev/null +++ b/driver/configure @@ -0,0 +1,32 @@ +#!/bin/sh + +gdev="gdev" +common="common" + +# configure options. +driver="pscnv" # use pscnv by default. +debug=0 + +# parse the given options. +for option +do + case "$option" in + -*=*) optarg=`echo "$option" | sed 's/[-_a-zA-Z0-9]*=//'` ;; + *) optarg= ;; + esac + + case "$option" in + --driver=*) + driver="$optarg" ;; + --debug) + debug=1 ;; + esac +done + +rm -f $gdev.ko +ln -s $driver.ko $gdev.ko +cp -fr ../$gdev/* ./ +cp -fr ../$driver/* ./ +cp -fr ../../$common/* ./ +cat ../$gdev/Makefile >> Makefile +./configure diff --git a/driver/gdev/Makefile b/driver/gdev/Makefile new file mode 100644 index 00000000..b0d0685f --- /dev/null +++ b/driver/gdev/Makefile @@ -0,0 +1,5 @@ + +.PHONY: install + +install: + @sh ./install.sh diff --git a/driver/gdev/gdev_drv.c b/driver/gdev/gdev_drv.c new file mode 100644 index 00000000..0a1bcadc --- /dev/null +++ b/driver/gdev/gdev_drv.c @@ -0,0 +1,238 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include +#include +#include +#include +#include +#include +#include + +#include "gdev_api.h" +#include "gdev_conf.h" +#include "gdev_drv.h" +#include "gdev_ioctl.h" + +struct gdev_drv gdrv; + +static int __get_devnum(struct file *filp) +{ + char *devname = filp->f_dentry->d_iname; + if (strncmp(devname, "gdev", 4) == 0) { + char *devnum = devname + 4; + return simple_strtoul(devnum, NULL, 10); + } + return -EINVAL; +} + +static int gdev_open(struct inode *inode, struct file *filp) +{ + int devnum; + gdev_handle_t *handle; + + if ((devnum = __get_devnum(filp)) < 0) { + GDEV_PRINT("Could not find device.\n"); + return -EINVAL; + } + + if (!(handle = gopen(devnum))) { + GDEV_PRINT("Out of resource.\n"); + return -ENOMEM; + } + + filp->private_data = handle; + + return 0; +} + +static int gdev_release(struct inode *inode, struct file *filp) +{ + gdev_handle_t *handle = filp->private_data; + + if (!handle) { + GDEV_PRINT("Device not opened.\n"); + return -ENOENT; + } + + return gclose(handle); +} + +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,37) +static long gdev_ioctl +(struct file *filp, unsigned int cmd, unsigned long arg) +#else +static int gdev_ioctl +(struct inode *inode, struct file *filp, unsigned int cmd, unsigned long arg) +#endif +{ + gdev_handle_t *handle = filp->private_data; + + switch (cmd) { + case GDEV_IOCTL_GMALLOC: + return gdev_ioctl_gmalloc(handle, arg); + case GDEV_IOCTL_GFREE: + return gdev_ioctl_gfree(handle, arg); + case GDEV_IOCTL_GMEMCPY_FROM_DEVICE: + return gdev_ioctl_gmemcpy_from_device(handle, arg); + case GDEV_IOCTL_GMEMCPY_TO_DEVICE: + return gdev_ioctl_gmemcpy_to_device(handle, arg); + case GDEV_IOCTL_GMEMCPY_IN_DEVICE: + return gdev_ioctl_gmemcpy_in_device(handle, arg); + case GDEV_IOCTL_GLAUNCH: + return gdev_ioctl_glaunch(handle, arg); + case GDEV_IOCTL_GSYNC: + return gdev_ioctl_gsync(handle, arg); + case GDEV_IOCTL_GQUERY: + return gdev_ioctl_gquery(handle, arg); + case GDEV_IOCTL_GTUNE: + return gdev_ioctl_gtune(handle, arg); + default: + GDEV_PRINT("Ioctl command 0x%x is not supported.\n", cmd); + return -EINVAL; + } + + return 0; +} + +static struct file_operations gdev_fops = { + .owner = THIS_MODULE, + .open = gdev_open, + .release = gdev_release, +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,37) + .unlocked_ioctl = gdev_ioctl, +#else + .ioctl = gdev_ioctl, +#endif +}; + +int gdev_minor_init(struct drm_device *drm) +{ + int ret; + int i = drm->primary->index; + struct gdev_device *gdev = &gdrv.gdev[i]; + + if (i >= gdrv.count) { + GDEV_PRINT("Could not find gdev%d.\n", i); + return -EINVAL; + } + + /* register a new character device. */ + GDEV_PRINT("Adding gdev%d.\n", i); + cdev_init(&gdev->cdev, &gdev_fops); + ret = cdev_add(&gdev->cdev, gdrv.dev, 1); + if (ret < 0) { + GDEV_PRINT("Failed to register gdev%d.\n", i); + return ret; + } + + /* initialize the Gdev compute engine. */ + gdev->id = i; + gdev->drm = drm; + gdev->use = 0; + gdev_compute_init(gdev); + + return 0; +} + +int gdev_minor_exit(struct drm_device *drm) +{ + int i = drm->primary->index; + struct gdev_device *gdev = &gdrv.gdev[i]; + + if (gdev->use) { + GDEV_PRINT("gdev%d still has %d users.\n", i, gdev->use); + } + + if (i < gdrv.count) { + GDEV_PRINT("Removing gdev%d.\n", i); + gdev->drm = NULL; + cdev_del(&gdev->cdev); + } + + return 0; +} + +int gdev_major_init(struct pci_driver *pdriver) +{ + int i, ret; + struct pci_dev *pdev = NULL; + const struct pci_device_id *pid; + + GDEV_PRINT("Initializing module...\n"); + + /* count how many devices are installed. */ + gdrv.count = 0; + for (i = 0; pdriver->id_table[i].vendor != 0; i++) { + pid = &pdriver->id_table[i]; + while ((pdev = + pci_get_subsys(pid->vendor, pid->device, pid->subvendor, + pid->subdevice, pdev)) != NULL) { + if ((pdev->class & pid->class_mask) != pid->class) + continue; + + gdrv.count++; + } + } + + GDEV_PRINT("Found %d GPU device(s).\n", gdrv.count); + + ret = alloc_chrdev_region(&gdrv.dev, 0, gdrv.count, MODULE_NAME); + if (ret < 0) { + GDEV_PRINT("Failed to allocate module.\n"); + return ret; + } + + /* allocate Gdev device objects. */ + gdrv.gdev = kmalloc(sizeof(struct gdev_device) * gdrv.count, GFP_KERNEL); + + return 0; +} + +int gdev_major_exit(void) +{ + GDEV_PRINT("Exiting module...\n"); + + kfree(gdrv.gdev); + unregister_chrdev_region(gdrv.dev, gdrv.count); + + return 0; +} + +/** + * export Gdev API functions. + */ +EXPORT_SYMBOL(gopen); +EXPORT_SYMBOL(gclose); +EXPORT_SYMBOL(gmalloc); +EXPORT_SYMBOL(gfree); +EXPORT_SYMBOL(gmemcpy_from_device); +EXPORT_SYMBOL(gmemcpy_user_from_device); +EXPORT_SYMBOL(gmemcpy_to_device); +EXPORT_SYMBOL(gmemcpy_user_to_device); +EXPORT_SYMBOL(gmemcpy_in_device); +EXPORT_SYMBOL(glaunch); +EXPORT_SYMBOL(gsync); +EXPORT_SYMBOL(gquery); +EXPORT_SYMBOL(gtune); diff --git a/driver/gdev/gdev_drv.h b/driver/gdev/gdev_drv.h new file mode 100644 index 00000000..06b1311e --- /dev/null +++ b/driver/gdev/gdev_drv.h @@ -0,0 +1,119 @@ +/* +* Copyright 2011 Shinpei Kato +* All Rights Reserved. +* +* Permission is hereby granted, free of charge, to any person obtaining a +* copy of this software and associated documentation files (the "Software"), +* to deal in the Software without restriction, including without limitation +* the rights to use, copy, modify, merge, publish, distribute, sublicense, +* and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice (including the next +* paragraph) shall be included in all copies or substantial portions of the +* Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +* VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR +* OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, +* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +* OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef __GDEV_DRV_H__ +#define __GDEV_DRV_H__ + +#include +#include +#include "drmP.h" +#include "drm.h" + +#define MODULE_NAME "gdev" + +#define GDEV_DEV_GET(handle) (handle)->gdev +#define GDEV_DEV_SET(handle, dev) (handle)->gdev = (dev) +#define GDEV_VAS_GET(handle) (handle)->vas +#define GDEV_VAS_SET(handle, vas) (handle)->vas = (vas) +#define GDEV_CTX_GET(handle) (handle)->ctx +#define GDEV_CTX_SET(handle, ctx) (handle)->ctx = (ctx) +#define GDEV_DMA_GET(handle) (handle)->dma_mem +#define GDEV_DMA_SET(handle, mem) (handle)->dma_mem = (mem) +#define GDEV_PIPELINE_GET(handle) (handle)->pipeline_count +#define GDEV_PIPELINE_SET(handle, val) (handle)->pipeline_count = val +#define GDEV_CHUNK_GET(handle) (handle)->chunk_size +#define GDEV_CHUNK_SET(handle, val) (handle)->chunk_size = val +#define GDEV_MINOR_GET(handle) (handle)->dev_id +#define GDEV_MINOR_SET(handle, val) (handle)->dev_id = val +#define GDEV_PRINT(fmt, arg...) printk("[gdev] " fmt, ##arg) +#define GDEV_DPRINT(fmt, arg...) \ + if (DEBUG_PRINT) \ + printk("[gdev:debug] " fmt, ##arg) + +#define MALLOC(x) kmalloc(x, GFP_KERNEL) +#define FREE(x) kfree(x) +#define SCHED_YIELD() schedule_timeout(1) +#define MB() mb() +#define COPY_FROM_USER(dst, src, size) \ + copy_from_user(dst, (void __user *) src, size) +#define COPY_TO_USER(dst, src, size) \ + copy_to_user((void __user *) dst, src, size) + +/** + * Gdev types: + */ +typedef struct gdev_vas gdev_vas_t; +typedef struct gdev_ctx gdev_ctx_t; +typedef struct gdev_mem gdev_mem_t; +typedef struct gdev_handle gdev_handle_t; +typedef struct gdev_device gdev_device_t; +typedef struct gdev_list_head gdev_list_t; + +/** + * Gdev handle struct: + */ +struct gdev_handle { + gdev_device_t *gdev; /* gdev handle object. */ + gdev_vas_t *vas; /* virtual address space object. */ + gdev_ctx_t *ctx; /* device context object. */ + gdev_mem_t **dma_mem; /* host-side DMA memory object (bounce buffer). */ + uint32_t chunk_size; /* configurable memcpy chunk size. */ + int pipeline_count; /* configurable memcpy pipeline count. */ + int dev_id; /* device ID. */ +}; + +/** +* Gdev driver module struct: +*/ +struct gdev_drv { + int count; + dev_t dev; + gdev_device_t *gdev; +}; + +/** + * Gdev device struct: + */ +struct gdev_device { + int id; + int use; /* the number of threads/processes using the device. */ + struct cdev cdev; /* character device object */ + struct drm_device *drm; /* DRM device object */ + void *compute; /* private set of compute functions */ +}; + +/** + * Gdev init/exit functions: + */ +int gdev_major_init(struct pci_driver*); +int gdev_major_exit(void); +int gdev_minor_init(struct drm_device*); +int gdev_minor_exit(struct drm_device*); + +/** + * Export the Gdev driver module object: + */ +extern struct gdev_drv gdrv; + +#endif diff --git a/driver/gdev/gdev_ioctl.c b/driver/gdev/gdev_ioctl.c new file mode 100644 index 00000000..ccb1c58e --- /dev/null +++ b/driver/gdev/gdev_ioctl.c @@ -0,0 +1,204 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "gdev_api.h" +#include "gdev_conf.h" +#include "gdev_ioctl.h" + +#define GDEV_MEMCPY_USER_DIRECT + +int gdev_ioctl_gmalloc(gdev_handle_t *handle, unsigned long arg) +{ + gdev_ioctl_mem_t m; + + if (copy_from_user(&m, (void __user *)arg, sizeof(m))) + return -EFAULT; + + if (!(m.addr = gmalloc(handle, m.size))) + return -ENOMEM; + + if (copy_to_user((void __user *)arg, &m, sizeof(m))) + return -EFAULT; + + return 0; +} + +int gdev_ioctl_gfree(gdev_handle_t *handle, unsigned long arg) +{ + gdev_ioctl_mem_t m; + + if (copy_from_user(&m, (void __user *)arg, sizeof(m))) + return -EFAULT; + gfree(handle, m.addr); + + return 0; +} + +int gdev_ioctl_gmemcpy_from_device(gdev_handle_t *handle, unsigned long arg) +{ + gdev_ioctl_dma_t dma; + int ret; +#ifndef GDEV_MEMCPY_USER_DIRECT + void *buf; +#endif + + if (copy_from_user(&dma, (void __user *)arg, sizeof(dma))) + return -EFAULT; + +#ifdef GDEV_MEMCPY_USER_DIRECT + ret = gmemcpy_user_from_device(handle, dma.dst_buf, dma.src_addr, dma.size); + if (ret) + return ret; +#else + if (dma.size > 0x400000) + buf = vmalloc(dma.size); + else + buf = kmalloc(dma.size, GFP_KERNEL); + + if (!buf) + return -ENOMEM; + + ret = gmemcpy_from_device(handle, buf, dma.src_addr, dma.size); + if (ret) + return ret; + + if (copy_to_user((void __user *)dma.dst_buf, buf, dma.size)) + return -EFAULT; + + if (dma.size > 0x400000) + vfree(buf); + else + kfree(buf); +#endif + + return 0; +} + +int gdev_ioctl_gmemcpy_to_device(gdev_handle_t *handle, unsigned long arg) +{ + gdev_ioctl_dma_t dma; + int ret; +#ifndef GDEV_MEMCPY_USER_DIRECT + void *buf; +#endif + + if (copy_from_user(&dma, (void __user *)arg, sizeof(dma))) + return -EFAULT; + +#ifdef GDEV_MEMCPY_USER_DIRECT + ret = gmemcpy_user_to_device(handle, dma.dst_addr, dma.src_buf, dma.size); + if (ret) + return ret; +#else + if (dma.size > 0x400000) + buf = vmalloc(dma.size); + else + buf = kmalloc(dma.size, GFP_KERNEL); + + if (!buf) + return -ENOMEM; + + if (copy_from_user(buf, (void __user *)dma.src_buf, dma.size)) + return -EFAULT; + + ret = gmemcpy_to_device(handle, dma.dst_addr, buf, dma.size); + if (ret) + return ret; + + if (dma.size > 0x400000) + vfree(buf); + else + kfree(buf); +#endif + + return 0; +} + +int gdev_ioctl_gmemcpy_in_device(gdev_handle_t *handle, unsigned long arg) +{ + gdev_ioctl_dma_t dma; + + if (copy_from_user(&dma, (void __user *)arg, sizeof(dma))) + return -EFAULT; + + gmemcpy_in_device(handle, dma.dst_addr, dma.src_addr, dma.size); + + return 0; +} + +int gdev_ioctl_glaunch(gdev_handle_t *handle, unsigned long arg) +{ + gdev_ioctl_launch_t launch; + struct gdev_kernel kernel; + uint32_t id; + + if (copy_from_user(&launch, (void __user *)arg, sizeof(launch))) + return -EFAULT; + + if (copy_from_user(&kernel, (void __user *)launch.kernel, sizeof(kernel))) + return -EFAULT; + + glaunch(handle, &kernel, &id); + + if (copy_to_user((void __user *)launch.id, &id, sizeof(id))) + return -EFAULT; + + return 0; +} + +int gdev_ioctl_gsync(gdev_handle_t *handle, unsigned long arg) +{ + gsync(handle, arg); + + return 0; +} + +int gdev_ioctl_gquery(gdev_handle_t *handle, unsigned long arg) +{ + gdev_ioctl_query_t q; + + if (copy_from_user(&q, (void __user *)arg, sizeof(q))) + return -EFAULT; + + if (gquery(handle, q.type, &q.result)) + return -EINVAL; + + if (copy_to_user((void __user *)arg, &q, sizeof(q))) + return -EFAULT; + + return 0; +} + +int gdev_ioctl_gtune(gdev_handle_t *handle, unsigned long arg) +{ + gdev_ioctl_tune_t c; + + if (copy_from_user(&c, (void __user *)arg, sizeof(c))) + return -EFAULT; + + if (gtune(handle, c.type, c.value)) + return -EINVAL; + + return 0; +} diff --git a/driver/gdev/gdev_ioctl.h b/driver/gdev/gdev_ioctl.h new file mode 100644 index 00000000..b8dd2e5e --- /dev/null +++ b/driver/gdev/gdev_ioctl.h @@ -0,0 +1,41 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __GDEV_IOCTL_H__ +#define __GDEV_IOCTL_H__ + +#include "gdev_api.h" +#include "gdev_ioctl_def.h" + +int gdev_ioctl_gmalloc(gdev_handle_t*, unsigned long); +int gdev_ioctl_gfree(gdev_handle_t*, unsigned long); +int gdev_ioctl_gmemcpy_from_device(gdev_handle_t*, unsigned long); +int gdev_ioctl_gmemcpy_to_device(gdev_handle_t*, unsigned long); +int gdev_ioctl_gmemcpy_in_device(gdev_handle_t*, unsigned long); +int gdev_ioctl_glaunch(gdev_handle_t*, unsigned long); +int gdev_ioctl_gsync(gdev_handle_t*, unsigned long); +int gdev_ioctl_gquery(gdev_handle_t*, unsigned long); +int gdev_ioctl_gtune(gdev_handle_t*, unsigned long); + +#endif diff --git a/driver/gdev/install.sh b/driver/gdev/install.sh new file mode 100644 index 00000000..e018f759 --- /dev/null +++ b/driver/gdev/install.sh @@ -0,0 +1,41 @@ +#!/bin/sh + +rmmod nvidia +rmmod nouveau +rmmod ttm +insmod ./gdev.ko + +# get a proper group +group="staff" +grep -q '^staff:' /etc/group || group="wheel" + +# remove stale nodes +rm -f /dev/gdev* + +# make nodes +major=$(awk "\$2==\"gdev\" {print \$1}" /proc/devices) +devnum=$(ls /dev/dri/card* | awk "{print \$1}" | wc -l) +minor=0 +while [ $minor -lt $devnum ] +do + mknod /dev/gdev${minor} c $major $minor + chgrp $group /dev/gdev${minor} + #chmod 664 /dev/gdev${minor} + chmod 666 /dev/gdev${minor} # just temporarily + minor=$(expr $minor + 1) +done + +gdevdir=/usr/local/gdev +gdevinc=$gdevdir/include +# install header files +if [ ! -d $gdevdir ]; then + mkdir $gdevdir +fi +if [ ! -d $gdevinc ]; then + mkdir $gdevinc +fi +cp -f Module.symvers $gdevdir +cp -f gdev_drv.h $gdevinc +cp -f gdev_api.h $gdevinc +cp -f gdev_nvidia_def.h $gdevinc + diff --git a/driver/pscnv/Makefile b/driver/pscnv/Makefile new file mode 100644 index 00000000..bd0f456c --- /dev/null +++ b/driver/pscnv/Makefile @@ -0,0 +1,40 @@ +pscnv-y := nouveau_drv.o nouveau_state.o \ + nouveau_irq.o nouveau_bios.o nouveau_hw.o nouveau_mem.o \ + nouveau_i2c.o nouveau_calc.o nouveau_dp.o nouveau_connector.o \ + nouveau_display.o nouveau_fbcon.o nouveau_dma.o \ + nouveau_pm.o nouveau_volt.o nouveau_perf.o nouveau_temp.o \ + nv04_tv.o nv04_dfp.o nv04_dac.o nv04_timer.o \ + nv10_gpio.o \ + nv50_gpio.o nv50_grctx.o \ + nv50_display.o nv50_crtc.o nv50_cursor.o nv50_calc.o nv50_dac.o \ + nv50_sor.o \ + nv04_pm.o nv50_pm.o nva3_pm.o \ + pscnv_mm.o pscnv_mem.o pscnv_vm.o pscnv_gem.o pscnv_ioctl.o \ + pscnv_ramht.o pscnv_chan.o pscnv_sysram.o \ + nv50_vram.o nv50_vm.o nv50_chan.o nv50_fifo.o nv50_graph.o \ + nv84_crypt.o \ + nv98_crypt.o \ + nvc0_vram.o nvc0_vm.o nvc0_chan.o nvc0_copy.o nvc0_fifo.o \ + nvc0_graph.o nvc0_grctx.o \ + pscnv_gdev.o \ + gdev_api.o gdev_drv.o gdev_ioctl.o gdev_nvidia.o \ + gdev_nvidia_nvc0.o + + +pscnv-$(CONFIG_DRM_NOUVEAU_DEBUG) += nouveau_debugfs.o +pscnv-$(CONFIG_COMPAT) += nouveau_ioc32.o +pscnv-$(CONFIG_DRM_NOUVEAU_BACKLIGHT) += nouveau_backlight.o +pscnv-$(CONFIG_ACPI) += nouveau_acpi.o + +obj-m := pscnv.o + +EXTRA_CFLAGS = -Iinclude/drm + +SYSSRC = /lib/modules/$(shell uname -r)/build + +all: + +make -C $(SYSSRC) M=$(PWD) modules + +clean: + +make -C $(SYSSRC) M=$(PWD) clean + rm -f pscnv_kapi.h *.fuc.h *~ diff --git a/driver/pscnv/configure b/driver/pscnv/configure new file mode 100755 index 00000000..3fcfeb27 --- /dev/null +++ b/driver/pscnv/configure @@ -0,0 +1,13 @@ +#!/bin/sh + +kver=`uname -r` +ksrc=/lib/modules/$kver/build + +echo 'Checking kernel functions...' +./kapitest.sh $ksrc > pscnv_kapi.h + +echo 'Generating firmware...' +m4 nvc0_grhub.fuc | envyas -a -w -m fuc -V nva3 -o nvc0_grhub.fuc.h +m4 nvc0_grgpc.fuc | envyas -a -w -m fuc -V nva3 -o nvc0_grgpc.fuc.h +m4 -DNVC0 nva3_copy.fuc | envyas -a -w -m fuc -V nva3 -o nvc0_copy.fuc.h +envyas -m fuc -a nv98_crypt.fuc -o nv98_crypt.fuc.h diff --git a/driver/pscnv/i2c/sil164.h b/driver/pscnv/i2c/sil164.h new file mode 100644 index 00000000..205e2738 --- /dev/null +++ b/driver/pscnv/i2c/sil164.h @@ -0,0 +1,63 @@ +/* + * Copyright (C) 2010 Francisco Jerez. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#ifndef __DRM_I2C_SIL164_H__ +#define __DRM_I2C_SIL164_H__ + +/** + * struct sil164_encoder_params + * + * Describes how the sil164 is connected to the GPU. It should be used + * as the @params parameter of its @set_config method. + * + * See "http://www.siliconimage.com/docs/SiI-DS-0021-E-164.pdf". + */ +struct sil164_encoder_params { + enum { + SIL164_INPUT_EDGE_FALLING = 0, + SIL164_INPUT_EDGE_RISING + } input_edge; + + enum { + SIL164_INPUT_WIDTH_12BIT = 0, + SIL164_INPUT_WIDTH_24BIT + } input_width; + + enum { + SIL164_INPUT_SINGLE_EDGE = 0, + SIL164_INPUT_DUAL_EDGE + } input_dual; + + enum { + SIL164_PLL_FILTER_ON = 0, + SIL164_PLL_FILTER_OFF, + } pll_filter; + + int input_skew; /** < Allowed range [-4, 3], use 0 for no de-skew. */ + int duallink_skew; /** < Allowed range [-4, 3]. */ +}; + +#endif diff --git a/driver/pscnv/kapitest.sh b/driver/pscnv/kapitest.sh new file mode 100755 index 00000000..4e9e9e9e --- /dev/null +++ b/driver/pscnv/kapitest.sh @@ -0,0 +1,13 @@ +#!/bin/sh +TESTS="gamma_set_5 gamma_set_6 drm_ioctl_def drm_ioctl_def_drv drm_connector_detect_1 drm_connector_detect_2 map_ofs io_mapping_2 io_mapping_3 i2c_id pci_driver switcheroo_reprobe getparam_bus_type drm_gem_object_handle_count" + +make -k -C $1 M=$PWD/kapitest clean &> /dev/null +make -k -C $1 M=$PWD/kapitest modules &> /dev/null + +for i in $TESTS +do + if [ -f kapitest/$i.o ] + then + echo \#define PSCNV_KAPI_`echo $i | tr a-z A-Z` + fi +done diff --git a/driver/pscnv/kapitest/Makefile b/driver/pscnv/kapitest/Makefile new file mode 100644 index 00000000..f0701a53 --- /dev/null +++ b/driver/pscnv/kapitest/Makefile @@ -0,0 +1,23 @@ +kapitest-y := fail.o \ + gamma_set_5.o gamma_set_6.o \ + drm_ioctl_def.o drm_ioctl_def_drv.o \ + drm_connector_detect_1.o drm_connector_detect_2.o \ + map_ofs.o \ + io_mapping_2.o io_mapping_3.o \ + i2c_id.o \ + pci_driver.o \ + switcheroo_reprobe.o \ + getparam_bus_type.o \ + drm_gem_object_handle_count.o + +obj-m := kapitest.o + +EXTRA_CFLAGS = -Iinclude/drm + +SYSSRC = /lib/modules/$(shell uname -r)/build + +all: + +make -C $(SYSSRC) M=$(PWD) modules + +clean: + +make -C $(SYSSRC) M=$(PWD) clean diff --git a/driver/pscnv/kapitest/drm_connector_detect_1.c b/driver/pscnv/kapitest/drm_connector_detect_1.c new file mode 100644 index 00000000..e899fc24 --- /dev/null +++ b/driver/pscnv/kapitest/drm_connector_detect_1.c @@ -0,0 +1,6 @@ +#include "drmP.h" +#include "drm_crtc.h" + +void dummy(struct drm_connector_funcs *funcs) { + funcs->detect(0); +} diff --git a/driver/pscnv/kapitest/drm_connector_detect_2.c b/driver/pscnv/kapitest/drm_connector_detect_2.c new file mode 100644 index 00000000..38edff73 --- /dev/null +++ b/driver/pscnv/kapitest/drm_connector_detect_2.c @@ -0,0 +1,6 @@ +#include "drmP.h" +#include "drm_crtc.h" + +void dummy(struct drm_connector_funcs *funcs) { + funcs->detect(0, 0); +} diff --git a/driver/pscnv/kapitest/drm_gem_object_handle_count.c b/driver/pscnv/kapitest/drm_gem_object_handle_count.c new file mode 100644 index 00000000..9c19e616 --- /dev/null +++ b/driver/pscnv/kapitest/drm_gem_object_handle_count.c @@ -0,0 +1,6 @@ +#include "drmP.h" + +void dummy(struct drm_gem_object *obj) +{ + atomic_inc(&obj->handle_count); +} diff --git a/driver/pscnv/kapitest/drm_ioctl_def.c b/driver/pscnv/kapitest/drm_ioctl_def.c new file mode 100644 index 00000000..32d06970 --- /dev/null +++ b/driver/pscnv/kapitest/drm_ioctl_def.c @@ -0,0 +1,7 @@ +#include "drm.h" +#include "drmP.h" +#include "nouveau_drm.h" + +struct drm_ioctl_desc nouveau_ioctls[] = { + DRM_IOCTL_DEF(DRM_NOUVEAU_GETPARAM, NULL, DRM_AUTH) +}; diff --git a/driver/pscnv/kapitest/drm_ioctl_def_drv.c b/driver/pscnv/kapitest/drm_ioctl_def_drv.c new file mode 100644 index 00000000..596340b5 --- /dev/null +++ b/driver/pscnv/kapitest/drm_ioctl_def_drv.c @@ -0,0 +1,7 @@ +#include "drm.h" +#include "drmP.h" +#include "nouveau_drm.h" + +struct drm_ioctl_desc nouveau_ioctls[] = { + DRM_IOCTL_DEF_DRV(NOUVEAU_GETPARAM, NULL, DRM_AUTH) +}; diff --git a/driver/pscnv/kapitest/fail.c b/driver/pscnv/kapitest/fail.c new file mode 100644 index 00000000..c7c8c2ff --- /dev/null +++ b/driver/pscnv/kapitest/fail.c @@ -0,0 +1 @@ +#error fail diff --git a/driver/pscnv/kapitest/gamma_set_5.c b/driver/pscnv/kapitest/gamma_set_5.c new file mode 100644 index 00000000..efdb0800 --- /dev/null +++ b/driver/pscnv/kapitest/gamma_set_5.c @@ -0,0 +1,7 @@ +#include "drm.h" +#include "drmP.h" +#include "drm_crtc.h" + +void dummy(struct drm_crtc_funcs *funcs) { + funcs->gamma_set(0, 0, 0, 0, 0); +} diff --git a/driver/pscnv/kapitest/gamma_set_6.c b/driver/pscnv/kapitest/gamma_set_6.c new file mode 100644 index 00000000..fe8be3c3 --- /dev/null +++ b/driver/pscnv/kapitest/gamma_set_6.c @@ -0,0 +1,7 @@ +#include "drm.h" +#include "drmP.h" +#include "drm_crtc.h" + +void dummy(struct drm_crtc_funcs *funcs) { + funcs->gamma_set(0, 0, 0, 0, 0, 0); +} diff --git a/driver/pscnv/kapitest/getparam_bus_type.c b/driver/pscnv/kapitest/getparam_bus_type.c new file mode 100644 index 00000000..0f26f62d --- /dev/null +++ b/driver/pscnv/kapitest/getparam_bus_type.c @@ -0,0 +1,8 @@ +#include "drmP.h" +#include "drm.h" + +void dummy(struct drm_device *dev) +{ + drm_device_is_agp(dev); + drm_device_is_pcie(dev); +} diff --git a/driver/pscnv/kapitest/i2c_id.c b/driver/pscnv/kapitest/i2c_id.c new file mode 100644 index 00000000..6741d960 --- /dev/null +++ b/driver/pscnv/kapitest/i2c_id.c @@ -0,0 +1,3 @@ +#include + +void dummy(void) {} diff --git a/driver/pscnv/kapitest/io_mapping_2.c b/driver/pscnv/kapitest/io_mapping_2.c new file mode 100644 index 00000000..4a1a25b5 --- /dev/null +++ b/driver/pscnv/kapitest/io_mapping_2.c @@ -0,0 +1,6 @@ +#include "drmP.h" +#include + +void dummy(struct io_mapping *iom) { + io_mapping_map_atomic_wc(iom, 0); +} diff --git a/driver/pscnv/kapitest/io_mapping_3.c b/driver/pscnv/kapitest/io_mapping_3.c new file mode 100644 index 00000000..dfe03705 --- /dev/null +++ b/driver/pscnv/kapitest/io_mapping_3.c @@ -0,0 +1,6 @@ +#include "drmP.h" +#include + +void dummy(struct io_mapping *iom) { + io_mapping_map_atomic_wc(iom, 0, 0); +} diff --git a/driver/pscnv/kapitest/map_ofs.c b/driver/pscnv/kapitest/map_ofs.c new file mode 100644 index 00000000..97cede6f --- /dev/null +++ b/driver/pscnv/kapitest/map_ofs.c @@ -0,0 +1,5 @@ +#include "drmP.h" + +void dummy (struct drm_driver *d) { + d->get_map_ofs = drm_core_get_map_ofs; +} diff --git a/driver/pscnv/kapitest/pci_driver.c b/driver/pscnv/kapitest/pci_driver.c new file mode 100644 index 00000000..c88c003a --- /dev/null +++ b/driver/pscnv/kapitest/pci_driver.c @@ -0,0 +1,9 @@ +#include "drmP.h" +#include "drm.h" + +void dummy(void) +{ + struct drm_driver driver; + /* driver.pci_driver = 0;*/ + drm_exit(&driver); +} diff --git a/driver/pscnv/kapitest/switcheroo_reprobe.c b/driver/pscnv/kapitest/switcheroo_reprobe.c new file mode 100644 index 00000000..4a1273aa --- /dev/null +++ b/driver/pscnv/kapitest/switcheroo_reprobe.c @@ -0,0 +1,8 @@ +#include "drmP.h" +#include "drm.h" +#include + +void dummy(struct drm_device *dev) +{ + vga_switcheroo_register_client(dev->pdev, 0, 0); +} diff --git a/driver/pscnv/nouveau_acpi.c b/driver/pscnv/nouveau_acpi.c new file mode 100644 index 00000000..f21bde3d --- /dev/null +++ b/driver/pscnv/nouveau_acpi.c @@ -0,0 +1,296 @@ +#include +#include +#include +#include +#include +#include + +#include "drmP.h" +#include "drm.h" +#include "drm_sarea.h" +#include "drm_crtc_helper.h" +#include "nouveau_drv.h" +#include "nv50_display.h" +#include "nouveau_connector.h" + +#include + +#define NOUVEAU_DSM_SUPPORTED 0x00 +#define NOUVEAU_DSM_SUPPORTED_FUNCTIONS 0x00 + +#define NOUVEAU_DSM_ACTIVE 0x01 +#define NOUVEAU_DSM_ACTIVE_QUERY 0x00 + +#define NOUVEAU_DSM_LED 0x02 +#define NOUVEAU_DSM_LED_STATE 0x00 +#define NOUVEAU_DSM_LED_OFF 0x10 +#define NOUVEAU_DSM_LED_STAMINA 0x11 +#define NOUVEAU_DSM_LED_SPEED 0x12 + +#define NOUVEAU_DSM_POWER 0x03 +#define NOUVEAU_DSM_POWER_STATE 0x00 +#define NOUVEAU_DSM_POWER_SPEED 0x01 +#define NOUVEAU_DSM_POWER_STAMINA 0x02 + +static struct nouveau_dsm_priv { + bool dsm_detected; + acpi_handle dhandle; + acpi_handle rom_handle; +} nouveau_dsm_priv; + +static const char nouveau_dsm_muid[] = { + 0xA0, 0xA0, 0x95, 0x9D, 0x60, 0x00, 0x48, 0x4D, + 0xB3, 0x4D, 0x7E, 0x5F, 0xEA, 0x12, 0x9F, 0xD4, +}; + +static int nouveau_dsm(acpi_handle handle, int func, int arg, uint32_t *result) +{ + struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; + struct acpi_object_list input; + union acpi_object params[4]; + union acpi_object *obj; + int err; + + input.count = 4; + input.pointer = params; + params[0].type = ACPI_TYPE_BUFFER; + params[0].buffer.length = sizeof(nouveau_dsm_muid); + params[0].buffer.pointer = (char *)nouveau_dsm_muid; + params[1].type = ACPI_TYPE_INTEGER; + params[1].integer.value = 0x00000102; + params[2].type = ACPI_TYPE_INTEGER; + params[2].integer.value = func; + params[3].type = ACPI_TYPE_INTEGER; + params[3].integer.value = arg; + + err = acpi_evaluate_object(handle, "_DSM", &input, &output); + if (err) { + printk(KERN_INFO "failed to evaluate _DSM: %d\n", err); + return err; + } + + obj = (union acpi_object *)output.pointer; + + if (obj->type == ACPI_TYPE_INTEGER) + if (obj->integer.value == 0x80000002) + return -ENODEV; + + if (obj->type == ACPI_TYPE_BUFFER) { + if (obj->buffer.length == 4 && result) { + *result = 0; + *result |= obj->buffer.pointer[0]; + *result |= (obj->buffer.pointer[1] << 8); + *result |= (obj->buffer.pointer[2] << 16); + *result |= (obj->buffer.pointer[3] << 24); + } + } + + kfree(output.pointer); + return 0; +} + +static int nouveau_dsm_switch_mux(acpi_handle handle, int mux_id) +{ + return nouveau_dsm(handle, NOUVEAU_DSM_LED, mux_id, NULL); +} + +static int nouveau_dsm_set_discrete_state(acpi_handle handle, enum vga_switcheroo_state state) +{ + int arg; + if (state == VGA_SWITCHEROO_ON) + arg = NOUVEAU_DSM_POWER_SPEED; + else + arg = NOUVEAU_DSM_POWER_STAMINA; + nouveau_dsm(handle, NOUVEAU_DSM_POWER, arg, NULL); + return 0; +} + +static int nouveau_dsm_switchto(enum vga_switcheroo_client_id id) +{ + if (id == VGA_SWITCHEROO_IGD) + return nouveau_dsm_switch_mux(nouveau_dsm_priv.dhandle, NOUVEAU_DSM_LED_STAMINA); + else + return nouveau_dsm_switch_mux(nouveau_dsm_priv.dhandle, NOUVEAU_DSM_LED_SPEED); +} + +static int nouveau_dsm_power_state(enum vga_switcheroo_client_id id, + enum vga_switcheroo_state state) +{ + if (id == VGA_SWITCHEROO_IGD) + return 0; + + return nouveau_dsm_set_discrete_state(nouveau_dsm_priv.dhandle, state); +} + +static int nouveau_dsm_init(void) +{ + return 0; +} + +static int nouveau_dsm_get_client_id(struct pci_dev *pdev) +{ + if (nouveau_dsm_priv.dhandle == DEVICE_ACPI_HANDLE(&pdev->dev)) + return VGA_SWITCHEROO_IGD; + else + return VGA_SWITCHEROO_DIS; +} + +static struct vga_switcheroo_handler nouveau_dsm_handler = { + .switchto = nouveau_dsm_switchto, + .power_state = nouveau_dsm_power_state, + .init = nouveau_dsm_init, + .get_client_id = nouveau_dsm_get_client_id, +}; + +static bool nouveau_dsm_pci_probe(struct pci_dev *pdev) +{ + acpi_handle dhandle, nvidia_handle; + acpi_status status; + int ret; + uint32_t result; + + dhandle = DEVICE_ACPI_HANDLE(&pdev->dev); + if (!dhandle) + return false; + + status = acpi_get_handle(dhandle, "_DSM", &nvidia_handle); + if (ACPI_FAILURE(status)) { + return false; + } + + ret = nouveau_dsm(dhandle, NOUVEAU_DSM_SUPPORTED, + NOUVEAU_DSM_SUPPORTED_FUNCTIONS, &result); + if (ret < 0) + return false; + + nouveau_dsm_priv.dhandle = dhandle; + return true; +} + +static bool nouveau_dsm_detect(void) +{ + char acpi_method_name[255] = { 0 }; + struct acpi_buffer buffer = {sizeof(acpi_method_name), acpi_method_name}; + struct pci_dev *pdev = NULL; + int has_dsm = 0; + int vga_count = 0; + + while ((pdev = pci_get_class(PCI_CLASS_DISPLAY_VGA << 8, pdev)) != NULL) { + vga_count++; + + has_dsm |= (nouveau_dsm_pci_probe(pdev) == true); + } + + if (vga_count == 2 && has_dsm) { + acpi_get_name(nouveau_dsm_priv.dhandle, ACPI_FULL_PATHNAME, &buffer); + printk(KERN_INFO "VGA switcheroo: detected DSM switching method %s handle\n", + acpi_method_name); + nouveau_dsm_priv.dsm_detected = true; + return true; + } + return false; +} + +void nouveau_register_dsm_handler(void) +{ + bool r; + + r = nouveau_dsm_detect(); + if (!r) + return; + + vga_switcheroo_register_handler(&nouveau_dsm_handler); +} + +void nouveau_unregister_dsm_handler(void) +{ + vga_switcheroo_unregister_handler(); +} + +/* retrieve the ROM in 4k blocks */ +static int nouveau_rom_call(acpi_handle rom_handle, uint8_t *bios, + int offset, int len) +{ + acpi_status status; + union acpi_object rom_arg_elements[2], *obj; + struct acpi_object_list rom_arg; + struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL}; + + rom_arg.count = 2; + rom_arg.pointer = &rom_arg_elements[0]; + + rom_arg_elements[0].type = ACPI_TYPE_INTEGER; + rom_arg_elements[0].integer.value = offset; + + rom_arg_elements[1].type = ACPI_TYPE_INTEGER; + rom_arg_elements[1].integer.value = len; + + status = acpi_evaluate_object(rom_handle, NULL, &rom_arg, &buffer); + if (ACPI_FAILURE(status)) { + printk(KERN_INFO "failed to evaluate ROM got %s\n", acpi_format_exception(status)); + return -ENODEV; + } + obj = (union acpi_object *)buffer.pointer; + memcpy(bios+offset, obj->buffer.pointer, len); + kfree(buffer.pointer); + return len; +} + +bool nouveau_acpi_rom_supported(struct pci_dev *pdev) +{ + acpi_status status; + acpi_handle dhandle, rom_handle; + + if (!nouveau_dsm_priv.dsm_detected) + return false; + + dhandle = DEVICE_ACPI_HANDLE(&pdev->dev); + if (!dhandle) + return false; + + status = acpi_get_handle(dhandle, "_ROM", &rom_handle); + if (ACPI_FAILURE(status)) + return false; + + nouveau_dsm_priv.rom_handle = rom_handle; + return true; +} + +int nouveau_acpi_get_bios_chunk(uint8_t *bios, int offset, int len) +{ + return nouveau_rom_call(nouveau_dsm_priv.rom_handle, bios, offset, len); +} + +int +nouveau_acpi_edid(struct drm_device *dev, struct drm_connector *connector) +{ + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct acpi_device *acpidev; + acpi_handle handle; + int type, ret; + void *edid; + + switch (connector->connector_type) { + case DRM_MODE_CONNECTOR_LVDS: + case DRM_MODE_CONNECTOR_eDP: + type = ACPI_VIDEO_DISPLAY_LCD; + break; + default: + return -EINVAL; + } + + handle = DEVICE_ACPI_HANDLE(&dev->pdev->dev); + if (!handle) + return -ENODEV; + + ret = acpi_bus_get_device(handle, &acpidev); + if (ret) + return -ENODEV; + + ret = acpi_video_get_edid(acpidev, type, -1, &edid); + if (ret < 0) + return ret; + + nv_connector->edid = kmemdup(edid, EDID_LENGTH, GFP_KERNEL); + return 0; +} diff --git a/driver/pscnv/nouveau_backlight.c b/driver/pscnv/nouveau_backlight.c new file mode 100644 index 00000000..85394993 --- /dev/null +++ b/driver/pscnv/nouveau_backlight.c @@ -0,0 +1,158 @@ +/* + * Copyright (C) 2009 Red Hat + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +/* + * Authors: + * Matthew Garrett + * + * Register locations derived from NVClock by Roderick Colenbrander + */ + +#include + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_reg.h" + +static int nv40_get_intensity(struct backlight_device *bd) +{ + struct drm_device *dev = bl_get_data(bd); + int val = (nv_rd32(dev, NV40_PMC_BACKLIGHT) & NV40_PMC_BACKLIGHT_MASK) + >> 16; + + return val; +} + +static int nv40_set_intensity(struct backlight_device *bd) +{ + struct drm_device *dev = bl_get_data(bd); + int val = bd->props.brightness; + int reg = nv_rd32(dev, NV40_PMC_BACKLIGHT); + + nv_wr32(dev, NV40_PMC_BACKLIGHT, + (val << 16) | (reg & ~NV40_PMC_BACKLIGHT_MASK)); + + return 0; +} + +static struct backlight_ops nv40_bl_ops = { + .options = BL_CORE_SUSPENDRESUME, + .get_brightness = nv40_get_intensity, + .update_status = nv40_set_intensity, +}; + +static int nv50_get_intensity(struct backlight_device *bd) +{ + struct drm_device *dev = bl_get_data(bd); + + return nv_rd32(dev, NV50_PDISPLAY_SOR_BACKLIGHT); +} + +static int nv50_set_intensity(struct backlight_device *bd) +{ + struct drm_device *dev = bl_get_data(bd); + int val = bd->props.brightness; + + nv_wr32(dev, NV50_PDISPLAY_SOR_BACKLIGHT, + val | NV50_PDISPLAY_SOR_BACKLIGHT_ENABLE); + return 0; +} + +static struct backlight_ops nv50_bl_ops = { + .options = BL_CORE_SUSPENDRESUME, + .get_brightness = nv50_get_intensity, + .update_status = nv50_set_intensity, +}; + +static int nouveau_nv40_backlight_init(struct drm_device *dev) +{ + struct backlight_properties props; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct backlight_device *bd; + + if (!(nv_rd32(dev, NV40_PMC_BACKLIGHT) & NV40_PMC_BACKLIGHT_MASK)) + return 0; + + memset(&props, 0, sizeof(struct backlight_properties)); + props.max_brightness = 31; + bd = backlight_device_register("nv_backlight", &dev->pdev->dev, dev, + &nv40_bl_ops, &props); + if (IS_ERR(bd)) + return PTR_ERR(bd); + + dev_priv->backlight = bd; + bd->props.brightness = nv40_get_intensity(bd); + backlight_update_status(bd); + + return 0; +} + +static int nouveau_nv50_backlight_init(struct drm_device *dev) +{ + struct backlight_properties props; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct backlight_device *bd; + + if (!nv_rd32(dev, NV50_PDISPLAY_SOR_BACKLIGHT)) + return 0; + + memset(&props, 0, sizeof(struct backlight_properties)); + props.max_brightness = 1025; + bd = backlight_device_register("nv_backlight", &dev->pdev->dev, dev, + &nv50_bl_ops, &props); + if (IS_ERR(bd)) + return PTR_ERR(bd); + + dev_priv->backlight = bd; + bd->props.brightness = nv50_get_intensity(bd); + backlight_update_status(bd); + return 0; +} + +int nouveau_backlight_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + switch (dev_priv->card_type) { + case NV_40: + return nouveau_nv40_backlight_init(dev); + case NV_50: + return nouveau_nv50_backlight_init(dev); + default: + break; + } + + return 0; +} + +void nouveau_backlight_exit(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + if (dev_priv->backlight) { + backlight_device_unregister(dev_priv->backlight); + dev_priv->backlight = NULL; + } +} diff --git a/driver/pscnv/nouveau_bios.c b/driver/pscnv/nouveau_bios.c new file mode 100644 index 00000000..2d4f1201 --- /dev/null +++ b/driver/pscnv/nouveau_bios.c @@ -0,0 +1,6933 @@ +/* + * Copyright 2005-2006 Erik Waling + * Copyright 2006 Stephane Marchesin + * Copyright 2007-2009 Stuart Bennett + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF + * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +#ifdef __linux__ +#include +#endif + +#include "drmP.h" +#define NV_DEBUG_NOTRACE +#include "nouveau_drv.h" +#include "nouveau_hw.h" +#include "nouveau_encoder.h" +#include "nouveau_reg.h" +#include "pscnv_kapi.h" + +#include + +/* these defines are made up */ +#define NV_CIO_CRE_44_HEADA 0x0 +#define NV_CIO_CRE_44_HEADB 0x3 +#define FEATURE_MOBILE 0x10 /* also FEATURE_QUADRO for BMP */ +#define LEGACY_I2C_CRT 0x80 +#define LEGACY_I2C_PANEL 0x81 +#define LEGACY_I2C_TV 0x82 + +#define EDID1_LEN 128 + +#define BIOSLOG(sip, fmt, arg...) NV_DEBUG(sip->dev, fmt, ##arg) +#define LOG_OLD_VALUE(x) + +struct init_exec { + bool execute; + bool repeat; +}; + +static bool nv_cksum(const uint8_t *data, unsigned int length) +{ + /* + * There's a few checksums in the BIOS, so here's a generic checking + * function. + */ + int i; + uint8_t sum = 0; + + for (i = 0; i < length; i++) + sum += data[i]; + + if (sum) + return true; + + return false; +} + +static int +score_vbios(struct drm_device *dev, const uint8_t *data, const bool writeable) +{ + if (!(data[0] == 0x55 && data[1] == 0xAA)) { + NV_TRACEWARN(dev, "... BIOS signature not found\n"); + return 0; + } + + if (nv_cksum(data, data[2] * 512)) { + NV_TRACEWARN(dev, "... BIOS checksum invalid\n"); + /* if a ro image is somewhat bad, it's probably all rubbish */ + return writeable ? 2 : 1; + } else + NV_TRACE(dev, "... appears to be valid\n"); + + return 3; +} + +static void load_vbios_prom(struct drm_device *dev, uint8_t *data) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t pci_nv_20, save_pci_nv_20; + int pcir_ptr; + int i; + + if (dev_priv->card_type >= NV_50) + pci_nv_20 = 0x88050; + else + pci_nv_20 = NV_PBUS_PCI_NV_20; + + /* enable ROM access */ + save_pci_nv_20 = nvReadMC(dev, pci_nv_20); + nvWriteMC(dev, pci_nv_20, + save_pci_nv_20 & ~NV_PBUS_PCI_NV_20_ROM_SHADOW_ENABLED); + + /* bail if no rom signature */ + if (nv_rd08(dev, NV_PROM_OFFSET) != 0x55 || + nv_rd08(dev, NV_PROM_OFFSET + 1) != 0xaa) + goto out; + + /* additional check (see note below) - read PCI record header */ + pcir_ptr = nv_rd08(dev, NV_PROM_OFFSET + 0x18) | + nv_rd08(dev, NV_PROM_OFFSET + 0x19) << 8; + if (nv_rd08(dev, NV_PROM_OFFSET + pcir_ptr) != 'P' || + nv_rd08(dev, NV_PROM_OFFSET + pcir_ptr + 1) != 'C' || + nv_rd08(dev, NV_PROM_OFFSET + pcir_ptr + 2) != 'I' || + nv_rd08(dev, NV_PROM_OFFSET + pcir_ptr + 3) != 'R') + goto out; + + /* on some 6600GT/6800LE prom reads are messed up. nvclock alleges a + * a good read may be obtained by waiting or re-reading (cargocult: 5x) + * each byte. we'll hope pramin has something usable instead + */ + for (i = 0; i < NV_PROM_SIZE; i++) + data[i] = nv_rd08(dev, NV_PROM_OFFSET + i); + +out: + /* disable ROM access */ + nvWriteMC(dev, pci_nv_20, + save_pci_nv_20 | NV_PBUS_PCI_NV_20_ROM_SHADOW_ENABLED); +} + +static void load_vbios_pramin(struct drm_device *dev, uint8_t *data) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t old_bar0_pramin = 0; + int i; + + if (dev_priv->card_type >= NV_50) { + uint32_t vbios_vram = (nv_rd32(dev, 0x619f04) & ~0xff) << 8; + + if (!vbios_vram) + vbios_vram = (nv_rd32(dev, 0x1700) << 16) + 0xf0000; + + old_bar0_pramin = nv_rd32(dev, 0x1700); + nv_wr32(dev, 0x1700, vbios_vram >> 16); + } + + /* bail if no rom signature */ + if (nv_rd08(dev, NV_PRAMIN_OFFSET) != 0x55 || + nv_rd08(dev, NV_PRAMIN_OFFSET + 1) != 0xaa) + goto out; + + for (i = 0; i < NV_PROM_SIZE; i++) + data[i] = nv_rd08(dev, NV_PRAMIN_OFFSET + i); + +out: + if (dev_priv->card_type >= NV_50) + nv_wr32(dev, 0x1700, old_bar0_pramin); +} + +static void load_vbios_pci(struct drm_device *dev, uint8_t *data) +{ + void __iomem *rom = NULL; + size_t rom_len; + int ret; + + ret = pci_enable_rom(dev->pdev); + if (ret) + return; + + rom = pci_map_rom(dev->pdev, &rom_len); + if (!rom) + goto out; + memcpy_fromio(data, rom, rom_len); + pci_unmap_rom(dev->pdev, rom); + +out: + pci_disable_rom(dev->pdev); +} + +static void load_vbios_acpi(struct drm_device *dev, uint8_t *data) +{ + int i; + int ret; + int size = 64 * 1024; + + if (!nouveau_acpi_rom_supported(dev->pdev)) + return; + + for (i = 0; i < (size / ROM_BIOS_PAGE); i++) { + ret = nouveau_acpi_get_bios_chunk(data, + (i * ROM_BIOS_PAGE), + ROM_BIOS_PAGE); + if (ret <= 0) + break; + } + return; +} + +struct methods { + const char desc[8]; + void (*loadbios)(struct drm_device *, uint8_t *); + const bool rw; +}; + +static struct methods shadow_methods[] = { + { "PRAMIN", load_vbios_pramin, true }, + { "PROM", load_vbios_prom, false }, + { "PCIROM", load_vbios_pci, true }, + { "ACPI", load_vbios_acpi, true }, +}; +#define NUM_SHADOW_METHODS ARRAY_SIZE(shadow_methods) + +static bool NVShadowVBIOS(struct drm_device *dev, uint8_t *data) +{ + struct methods *methods = shadow_methods; + int testscore = 3; + int scores[NUM_SHADOW_METHODS], i; + + if (nouveau_vbios) { + for (i = 0; i < NUM_SHADOW_METHODS; i++) + if (!strcasecmp(nouveau_vbios, methods[i].desc)) + break; + + if (i < NUM_SHADOW_METHODS) { + NV_INFO(dev, "Attempting to use BIOS image from %s\n", + methods[i].desc); + + methods[i].loadbios(dev, data); + if (score_vbios(dev, data, methods[i].rw)) + return true; + } + + NV_ERROR(dev, "VBIOS source \'%s\' invalid\n", nouveau_vbios); + } + + for (i = 0; i < NUM_SHADOW_METHODS; i++) { + NV_TRACE(dev, "Attempting to load BIOS image from %s\n", + methods[i].desc); + data[0] = data[1] = 0; /* avoid reuse of previous image */ + methods[i].loadbios(dev, data); + scores[i] = score_vbios(dev, data, methods[i].rw); + if (scores[i] == testscore) + return true; + } + + while (--testscore > 0) { + for (i = 0; i < NUM_SHADOW_METHODS; i++) { + if (scores[i] == testscore) { + NV_TRACE(dev, "Using BIOS image from %s\n", + methods[i].desc); + methods[i].loadbios(dev, data); + return true; + } + } + } + + NV_ERROR(dev, "No valid BIOS image found\n"); + return false; +} + +struct init_tbl_entry { + char *name; + uint8_t id; + /* Return: + * > 0: success, length of opcode + * 0: success, but abort further parsing of table (INIT_DONE etc) + * < 0: failure, table parsing will be aborted + */ + int (*handler)(struct nvbios *, uint16_t, struct init_exec *); +}; + +static int parse_init_table(struct nvbios *, unsigned int, struct init_exec *); + +#define MACRO_INDEX_SIZE 2 +#define MACRO_SIZE 8 +#define CONDITION_SIZE 12 +#define IO_FLAG_CONDITION_SIZE 9 +#define IO_CONDITION_SIZE 5 +#define MEM_INIT_SIZE 66 + +static void still_alive(void) +{ +#if 0 + sync(); + msleep(2); +#endif +} + +static uint32_t +munge_reg(struct nvbios *bios, uint32_t reg) +{ + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + struct dcb_entry *dcbent = bios->display.output; + + if (dev_priv->card_type < NV_50) + return reg; + + if (reg & 0x40000000) { + BUG_ON(!dcbent); + + reg += (ffs(dcbent->or) - 1) * 0x800; + if ((reg & 0x20000000) && !(dcbent->sorconf.link & 1)) + reg += 0x00000080; + } + + reg &= ~0x60000000; + return reg; +} + +static int +valid_reg(struct nvbios *bios, uint32_t reg) +{ + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + struct drm_device *dev = bios->dev; + + /* C51 has misaligned regs on purpose. Marvellous */ + if (reg & 0x2 || + (reg & 0x1 && dev_priv->vbios.chip_version != 0x51)) + NV_ERROR(dev, "======= misaligned reg 0x%08X =======\n", reg); + + /* warn on C51 regs that haven't been verified accessible in tracing */ + if (reg & 0x1 && dev_priv->vbios.chip_version == 0x51 && + reg != 0x130d && reg != 0x1311 && reg != 0x60081d) + NV_WARN(dev, "=== C51 misaligned reg 0x%08X not verified ===\n", + reg); + + if (reg >= (8*1024*1024)) { + NV_ERROR(dev, "=== reg 0x%08x out of mapped bounds ===\n", reg); + return 0; + } + + return 1; +} + +static bool +valid_idx_port(struct nvbios *bios, uint16_t port) +{ + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + struct drm_device *dev = bios->dev; + + /* + * If adding more ports here, the read/write functions below will need + * updating so that the correct mmio range (PRMCIO, PRMDIO, PRMVIO) is + * used for the port in question + */ + if (dev_priv->card_type < NV_50) { + if (port == NV_CIO_CRX__COLOR) + return true; + if (port == NV_VIO_SRX) + return true; + } else { + if (port == NV_CIO_CRX__COLOR) + return true; + } + + NV_ERROR(dev, "========== unknown indexed io port 0x%04X ==========\n", + port); + + return false; +} + +static bool +valid_port(struct nvbios *bios, uint16_t port) +{ + struct drm_device *dev = bios->dev; + + /* + * If adding more ports here, the read/write functions below will need + * updating so that the correct mmio range (PRMCIO, PRMDIO, PRMVIO) is + * used for the port in question + */ + if (port == NV_VIO_VSE2) + return true; + + NV_ERROR(dev, "========== unknown io port 0x%04X ==========\n", port); + + return false; +} + +static uint32_t +bios_rd32(struct nvbios *bios, uint32_t reg) +{ + uint32_t data; + + reg = munge_reg(bios, reg); + if (!valid_reg(bios, reg)) + return 0; + + /* + * C51 sometimes uses regs with bit0 set in the address. For these + * cases there should exist a translation in a BIOS table to an IO + * port address which the BIOS uses for accessing the reg + * + * These only seem to appear for the power control regs to a flat panel, + * and the GPIO regs at 0x60081*. In C51 mmio traces the normal regs + * for 0x1308 and 0x1310 are used - hence the mask below. An S3 + * suspend-resume mmio trace from a C51 will be required to see if this + * is true for the power microcode in 0x14.., or whether the direct IO + * port access method is needed + */ + if (reg & 0x1) + reg &= ~0x1; + + data = nv_rd32(bios->dev, reg); + + BIOSLOG(bios, " Read: Reg: 0x%08X, Data: 0x%08X\n", reg, data); + + return data; +} + +static void +bios_wr32(struct nvbios *bios, uint32_t reg, uint32_t data) +{ + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + + reg = munge_reg(bios, reg); + if (!valid_reg(bios, reg)) + return; + + /* see note in bios_rd32 */ + if (reg & 0x1) + reg &= 0xfffffffe; + + LOG_OLD_VALUE(bios_rd32(bios, reg)); + BIOSLOG(bios, " Write: Reg: 0x%08X, Data: 0x%08X\n", reg, data); + + if (dev_priv->vbios.execute) { + still_alive(); + nv_wr32(bios->dev, reg, data); + } +} + +static uint8_t +bios_idxprt_rd(struct nvbios *bios, uint16_t port, uint8_t index) +{ + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + struct drm_device *dev = bios->dev; + uint8_t data; + + if (!valid_idx_port(bios, port)) + return 0; + + if (dev_priv->card_type < NV_50) { + if (port == NV_VIO_SRX) + data = NVReadVgaSeq(dev, bios->state.crtchead, index); + else /* assume NV_CIO_CRX__COLOR */ + data = NVReadVgaCrtc(dev, bios->state.crtchead, index); + } else { + uint32_t data32; + + data32 = bios_rd32(bios, NV50_PDISPLAY_VGACRTC(index & ~3)); + data = (data32 >> ((index & 3) << 3)) & 0xff; + } + + BIOSLOG(bios, " Indexed IO read: Port: 0x%04X, Index: 0x%02X, " + "Head: 0x%02X, Data: 0x%02X\n", + port, index, bios->state.crtchead, data); + return data; +} + +static void +bios_idxprt_wr(struct nvbios *bios, uint16_t port, uint8_t index, uint8_t data) +{ + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + struct drm_device *dev = bios->dev; + + if (!valid_idx_port(bios, port)) + return; + + /* + * The current head is maintained in the nvbios member state.crtchead. + * We trap changes to CR44 and update the head variable and hence the + * register set written. + * As CR44 only exists on CRTC0, we update crtchead to head0 in advance + * of the write, and to head1 after the write + */ + if (port == NV_CIO_CRX__COLOR && index == NV_CIO_CRE_44 && + data != NV_CIO_CRE_44_HEADB) + bios->state.crtchead = 0; + + LOG_OLD_VALUE(bios_idxprt_rd(bios, port, index)); + BIOSLOG(bios, " Indexed IO write: Port: 0x%04X, Index: 0x%02X, " + "Head: 0x%02X, Data: 0x%02X\n", + port, index, bios->state.crtchead, data); + + if (bios->execute && dev_priv->card_type < NV_50) { + still_alive(); + if (port == NV_VIO_SRX) + NVWriteVgaSeq(dev, bios->state.crtchead, index, data); + else /* assume NV_CIO_CRX__COLOR */ + NVWriteVgaCrtc(dev, bios->state.crtchead, index, data); + } else + if (bios->execute) { + uint32_t data32, shift = (index & 3) << 3; + + still_alive(); + + data32 = bios_rd32(bios, NV50_PDISPLAY_VGACRTC(index & ~3)); + data32 &= ~(0xff << shift); + data32 |= (data << shift); + bios_wr32(bios, NV50_PDISPLAY_VGACRTC(index & ~3), data32); + } + + if (port == NV_CIO_CRX__COLOR && + index == NV_CIO_CRE_44 && data == NV_CIO_CRE_44_HEADB) + bios->state.crtchead = 1; +} + +static uint8_t +bios_port_rd(struct nvbios *bios, uint16_t port) +{ + uint8_t data, head = bios->state.crtchead; + + if (!valid_port(bios, port)) + return 0; + + data = NVReadPRMVIO(bios->dev, head, NV_PRMVIO0_OFFSET + port); + + BIOSLOG(bios, " IO read: Port: 0x%04X, Head: 0x%02X, Data: 0x%02X\n", + port, head, data); + + return data; +} + +static void +bios_port_wr(struct nvbios *bios, uint16_t port, uint8_t data) +{ + int head = bios->state.crtchead; + + if (!valid_port(bios, port)) + return; + + LOG_OLD_VALUE(bios_port_rd(bios, port)); + BIOSLOG(bios, " IO write: Port: 0x%04X, Head: 0x%02X, Data: 0x%02X\n", + port, head, data); + + if (!bios->execute) + return; + + still_alive(); + NVWritePRMVIO(bios->dev, head, NV_PRMVIO0_OFFSET + port, data); +} + +static bool +io_flag_condition_met(struct nvbios *bios, uint16_t offset, uint8_t cond) +{ + /* + * The IO flag condition entry has 2 bytes for the CRTC port; 1 byte + * for the CRTC index; 1 byte for the mask to apply to the value + * retrieved from the CRTC; 1 byte for the shift right to apply to the + * masked CRTC value; 2 bytes for the offset to the flag array, to + * which the shifted value is added; 1 byte for the mask applied to the + * value read from the flag array; and 1 byte for the value to compare + * against the masked byte from the flag table. + */ + + uint16_t condptr = bios->io_flag_condition_tbl_ptr + cond * IO_FLAG_CONDITION_SIZE; + uint16_t crtcport = ROM16(bios->data[condptr]); + uint8_t crtcindex = bios->data[condptr + 2]; + uint8_t mask = bios->data[condptr + 3]; + uint8_t shift = bios->data[condptr + 4]; + uint16_t flagarray = ROM16(bios->data[condptr + 5]); + uint8_t flagarraymask = bios->data[condptr + 7]; + uint8_t cmpval = bios->data[condptr + 8]; + uint8_t data; + + BIOSLOG(bios, "0x%04X: Port: 0x%04X, Index: 0x%02X, Mask: 0x%02X, " + "Shift: 0x%02X, FlagArray: 0x%04X, FAMask: 0x%02X, " + "Cmpval: 0x%02X\n", + offset, crtcport, crtcindex, mask, shift, flagarray, flagarraymask, cmpval); + + data = bios_idxprt_rd(bios, crtcport, crtcindex); + + data = bios->data[flagarray + ((data & mask) >> shift)]; + data &= flagarraymask; + + BIOSLOG(bios, "0x%04X: Checking if 0x%02X equals 0x%02X\n", + offset, data, cmpval); + + return (data == cmpval); +} + +static bool +bios_condition_met(struct nvbios *bios, uint16_t offset, uint8_t cond) +{ + /* + * The condition table entry has 4 bytes for the address of the + * register to check, 4 bytes for a mask to apply to the register and + * 4 for a test comparison value + */ + + uint16_t condptr = bios->condition_tbl_ptr + cond * CONDITION_SIZE; + uint32_t reg = ROM32(bios->data[condptr]); + uint32_t mask = ROM32(bios->data[condptr + 4]); + uint32_t cmpval = ROM32(bios->data[condptr + 8]); + uint32_t data; + + BIOSLOG(bios, "0x%04X: Cond: 0x%02X, Reg: 0x%08X, Mask: 0x%08X\n", + offset, cond, reg, mask); + + data = bios_rd32(bios, reg) & mask; + + BIOSLOG(bios, "0x%04X: Checking if 0x%08X equals 0x%08X\n", + offset, data, cmpval); + + return (data == cmpval); +} + +static bool +io_condition_met(struct nvbios *bios, uint16_t offset, uint8_t cond) +{ + /* + * The IO condition entry has 2 bytes for the IO port address; 1 byte + * for the index to write to io_port; 1 byte for the mask to apply to + * the byte read from io_port+1; and 1 byte for the value to compare + * against the masked byte. + */ + + uint16_t condptr = bios->io_condition_tbl_ptr + cond * IO_CONDITION_SIZE; + uint16_t io_port = ROM16(bios->data[condptr]); + uint8_t port_index = bios->data[condptr + 2]; + uint8_t mask = bios->data[condptr + 3]; + uint8_t cmpval = bios->data[condptr + 4]; + + uint8_t data = bios_idxprt_rd(bios, io_port, port_index) & mask; + + BIOSLOG(bios, "0x%04X: Checking if 0x%02X equals 0x%02X\n", + offset, data, cmpval); + + return (data == cmpval); +} + +static int +nv50_pll_set(struct drm_device *dev, uint32_t reg, uint32_t clk) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t reg0 = nv_rd32(dev, reg + 0); + uint32_t reg1 = nv_rd32(dev, reg + 4); + struct nouveau_pll_vals pll; + struct pll_lims pll_limits; + int ret; + + ret = get_pll_limits(dev, reg, &pll_limits); + if (ret) + return ret; + + clk = nouveau_calc_pll_mnp(dev, &pll_limits, clk, &pll); + if (!clk) + return -ERANGE; + + reg0 = (reg0 & 0xfff8ffff) | (pll.log2P << 16); + reg1 = (reg1 & 0xffff0000) | (pll.N1 << 8) | pll.M1; + + if (dev_priv->vbios.execute) { + still_alive(); + nv_wr32(dev, reg + 4, reg1); + nv_wr32(dev, reg + 0, reg0); + } + + return 0; +} + +static int +setPLL(struct nvbios *bios, uint32_t reg, uint32_t clk) +{ + struct drm_device *dev = bios->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + /* clk in kHz */ + struct pll_lims pll_lim; + struct nouveau_pll_vals pllvals; + int ret; + + if (dev_priv->card_type >= NV_50) + return nv50_pll_set(dev, reg, clk); + + /* high regs (such as in the mac g5 table) are not -= 4 */ + ret = get_pll_limits(dev, reg > 0x405c ? reg : reg - 4, &pll_lim); + if (ret) + return ret; + + clk = nouveau_calc_pll_mnp(dev, &pll_lim, clk, &pllvals); + if (!clk) + return -ERANGE; + + if (bios->execute) { + still_alive(); + nouveau_hw_setpll(dev, reg, &pllvals); + } + + return 0; +} + +static int dcb_entry_idx_from_crtchead(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + + /* + * For the results of this function to be correct, CR44 must have been + * set (using bios_idxprt_wr to set crtchead), CR58 set for CR57 = 0, + * and the DCB table parsed, before the script calling the function is + * run. run_digital_op_script is example of how to do such setup + */ + + uint8_t dcb_entry = NVReadVgaCrtc5758(dev, bios->state.crtchead, 0); + + if (dcb_entry > bios->dcb.entries) { + NV_ERROR(dev, "CR58 doesn't have a valid DCB entry currently " + "(%02X)\n", dcb_entry); + dcb_entry = 0x7f; /* unused / invalid marker */ + } + + return dcb_entry; +} + +static int +read_dcb_i2c_entry(struct drm_device *dev, int dcb_version, uint8_t *i2ctable, int index, struct dcb_i2c_entry *i2c) +{ + uint8_t dcb_i2c_ver = dcb_version, headerlen = 0, entry_len = 4; + int i2c_entries = DCB_MAX_NUM_I2C_ENTRIES; + int recordoffset = 0, rdofs = 1, wrofs = 0; + uint8_t port_type = 0; + + if (!i2ctable) + return -EINVAL; + + if (dcb_version >= 0x30) { + if (i2ctable[0] != dcb_version) /* necessary? */ + NV_WARN(dev, + "DCB I2C table version mismatch (%02X vs %02X)\n", + i2ctable[0], dcb_version); + dcb_i2c_ver = i2ctable[0]; + headerlen = i2ctable[1]; + if (i2ctable[2] <= DCB_MAX_NUM_I2C_ENTRIES) + i2c_entries = i2ctable[2]; + else + NV_WARN(dev, + "DCB I2C table has more entries than indexable " + "(%d entries, max %d)\n", i2ctable[2], + DCB_MAX_NUM_I2C_ENTRIES); + entry_len = i2ctable[3]; + /* [4] is i2c_default_indices, read in parse_dcb_table() */ + } + /* + * It's your own fault if you call this function on a DCB 1.1 BIOS -- + * the test below is for DCB 1.2 + */ + if (dcb_version < 0x14) { + recordoffset = 2; + rdofs = 0; + wrofs = 1; + } + + if (index == 0xf) + return 0; + if (index >= i2c_entries) { + NV_ERROR(dev, "DCB I2C index too big (%d >= %d)\n", + index, i2ctable[2]); + return -ENOENT; + } + if (i2ctable[headerlen + entry_len * index + 3] == 0xff) { + NV_ERROR(dev, "DCB I2C entry invalid\n"); + return -EINVAL; + } + + if (dcb_i2c_ver >= 0x30) { + port_type = i2ctable[headerlen + recordoffset + 3 + entry_len * index]; + + /* + * Fixup for chips using same address offset for read and + * write. + */ + if (port_type == 4) /* seen on C51 */ + rdofs = wrofs = 1; + if (port_type >= 5) /* G80+ */ + rdofs = wrofs = 0; + } + + if (dcb_i2c_ver >= 0x40) { + if (port_type != 5 && port_type != 6) + NV_WARN(dev, "DCB I2C table has port type %d\n", port_type); + + i2c->entry = ROM32(i2ctable[headerlen + recordoffset + entry_len * index]); + } + + i2c->port_type = port_type; + i2c->read = i2ctable[headerlen + recordoffset + rdofs + entry_len * index]; + i2c->write = i2ctable[headerlen + recordoffset + wrofs + entry_len * index]; + + return 0; +} + +static struct nouveau_i2c_chan * +init_i2c_device_find(struct drm_device *dev, int i2c_index) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct dcb_table *dcb = &dev_priv->vbios.dcb; + + if (i2c_index == 0xff) { + /* note: dcb_entry_idx_from_crtchead needs pre-script set-up */ + int idx = dcb_entry_idx_from_crtchead(dev), shift = 0; + int default_indices = dcb->i2c_default_indices; + + if (idx != 0x7f && dcb->entry[idx].i2c_upper_default) + shift = 4; + + i2c_index = (default_indices >> shift) & 0xf; + } + if (i2c_index == 0x80) /* g80+ */ + i2c_index = dcb->i2c_default_indices & 0xf; + else + if (i2c_index == 0x81) + i2c_index = (dcb->i2c_default_indices & 0xf0) >> 4; + + if (i2c_index >= DCB_MAX_NUM_I2C_ENTRIES) { + NV_ERROR(dev, "invalid i2c_index 0x%x\n", i2c_index); + return NULL; + } + + /* Make sure i2c table entry has been parsed, it may not + * have been if this is a bus not referenced by a DCB encoder + */ + read_dcb_i2c_entry(dev, dcb->version, dcb->i2c_table, + i2c_index, &dcb->i2c[i2c_index]); + + return nouveau_i2c_find(dev, i2c_index); +} + +static uint32_t +get_tmds_index_reg(struct drm_device *dev, uint8_t mlv) +{ + /* + * For mlv < 0x80, it is an index into a table of TMDS base addresses. + * For mlv == 0x80 use the "or" value of the dcb_entry indexed by + * CR58 for CR57 = 0 to index a table of offsets to the basic + * 0x6808b0 address. + * For mlv == 0x81 use the "or" value of the dcb_entry indexed by + * CR58 for CR57 = 0 to index a table of offsets to the basic + * 0x6808b0 address, and then flip the offset by 8. + */ + + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + const int pramdac_offset[13] = { + 0, 0, 0x8, 0, 0x2000, 0, 0, 0, 0x2008, 0, 0, 0, 0x2000 }; + const uint32_t pramdac_table[4] = { + 0x6808b0, 0x6808b8, 0x6828b0, 0x6828b8 }; + + if (mlv >= 0x80) { + int dcb_entry, dacoffset; + + /* note: dcb_entry_idx_from_crtchead needs pre-script set-up */ + dcb_entry = dcb_entry_idx_from_crtchead(dev); + if (dcb_entry == 0x7f) + return 0; + dacoffset = pramdac_offset[bios->dcb.entry[dcb_entry].or]; + if (mlv == 0x81) + dacoffset ^= 8; + return 0x6808b0 + dacoffset; + } else { + if (mlv >= ARRAY_SIZE(pramdac_table)) { + NV_ERROR(dev, "Magic Lookup Value too big (%02X)\n", + mlv); + return 0; + } + return pramdac_table[mlv]; + } +} + +static int +init_io_restrict_prog(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_IO_RESTRICT_PROG opcode: 0x32 ('2') + * + * offset (8 bit): opcode + * offset + 1 (16 bit): CRTC port + * offset + 3 (8 bit): CRTC index + * offset + 4 (8 bit): mask + * offset + 5 (8 bit): shift + * offset + 6 (8 bit): count + * offset + 7 (32 bit): register + * offset + 11 (32 bit): configuration 1 + * ... + * + * Starting at offset + 11 there are "count" 32 bit values. + * To find out which value to use read index "CRTC index" on "CRTC + * port", AND this value with "mask" and then bit shift right "shift" + * bits. Read the appropriate value using this index and write to + * "register" + */ + + uint16_t crtcport = ROM16(bios->data[offset + 1]); + uint8_t crtcindex = bios->data[offset + 3]; + uint8_t mask = bios->data[offset + 4]; + uint8_t shift = bios->data[offset + 5]; + uint8_t count = bios->data[offset + 6]; + uint32_t reg = ROM32(bios->data[offset + 7]); + uint8_t config; + uint32_t configval; + int len = 11 + count * 4; + + if (!iexec->execute) + return len; + + BIOSLOG(bios, "0x%04X: Port: 0x%04X, Index: 0x%02X, Mask: 0x%02X, " + "Shift: 0x%02X, Count: 0x%02X, Reg: 0x%08X\n", + offset, crtcport, crtcindex, mask, shift, count, reg); + + config = (bios_idxprt_rd(bios, crtcport, crtcindex) & mask) >> shift; + if (config > count) { + NV_ERROR(bios->dev, + "0x%04X: Config 0x%02X exceeds maximal bound 0x%02X\n", + offset, config, count); + return len; + } + + configval = ROM32(bios->data[offset + 11 + config * 4]); + + BIOSLOG(bios, "0x%04X: Writing config %02X\n", offset, config); + + bios_wr32(bios, reg, configval); + + return len; +} + +static int +init_repeat(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_REPEAT opcode: 0x33 ('3') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): count + * + * Execute script following this opcode up to INIT_REPEAT_END + * "count" times + */ + + uint8_t count = bios->data[offset + 1]; + uint8_t i; + + /* no iexec->execute check by design */ + + BIOSLOG(bios, "0x%04X: Repeating following segment %d times\n", + offset, count); + + iexec->repeat = true; + + /* + * count - 1, as the script block will execute once when we leave this + * opcode -- this is compatible with bios behaviour as: + * a) the block is always executed at least once, even if count == 0 + * b) the bios interpreter skips to the op following INIT_END_REPEAT, + * while we don't + */ + for (i = 0; i < count - 1; i++) + parse_init_table(bios, offset + 2, iexec); + + iexec->repeat = false; + + return 2; +} + +static int +init_io_restrict_pll(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_IO_RESTRICT_PLL opcode: 0x34 ('4') + * + * offset (8 bit): opcode + * offset + 1 (16 bit): CRTC port + * offset + 3 (8 bit): CRTC index + * offset + 4 (8 bit): mask + * offset + 5 (8 bit): shift + * offset + 6 (8 bit): IO flag condition index + * offset + 7 (8 bit): count + * offset + 8 (32 bit): register + * offset + 12 (16 bit): frequency 1 + * ... + * + * Starting at offset + 12 there are "count" 16 bit frequencies (10kHz). + * Set PLL register "register" to coefficients for frequency n, + * selected by reading index "CRTC index" of "CRTC port" ANDed with + * "mask" and shifted right by "shift". + * + * If "IO flag condition index" > 0, and condition met, double + * frequency before setting it. + */ + + uint16_t crtcport = ROM16(bios->data[offset + 1]); + uint8_t crtcindex = bios->data[offset + 3]; + uint8_t mask = bios->data[offset + 4]; + uint8_t shift = bios->data[offset + 5]; + int8_t io_flag_condition_idx = bios->data[offset + 6]; + uint8_t count = bios->data[offset + 7]; + uint32_t reg = ROM32(bios->data[offset + 8]); + uint8_t config; + uint16_t freq; + int len = 12 + count * 2; + + if (!iexec->execute) + return len; + + BIOSLOG(bios, "0x%04X: Port: 0x%04X, Index: 0x%02X, Mask: 0x%02X, " + "Shift: 0x%02X, IO Flag Condition: 0x%02X, " + "Count: 0x%02X, Reg: 0x%08X\n", + offset, crtcport, crtcindex, mask, shift, + io_flag_condition_idx, count, reg); + + config = (bios_idxprt_rd(bios, crtcport, crtcindex) & mask) >> shift; + if (config > count) { + NV_ERROR(bios->dev, + "0x%04X: Config 0x%02X exceeds maximal bound 0x%02X\n", + offset, config, count); + return len; + } + + freq = ROM16(bios->data[offset + 12 + config * 2]); + + if (io_flag_condition_idx > 0) { + if (io_flag_condition_met(bios, offset, io_flag_condition_idx)) { + BIOSLOG(bios, "0x%04X: Condition fulfilled -- " + "frequency doubled\n", offset); + freq *= 2; + } else + BIOSLOG(bios, "0x%04X: Condition not fulfilled -- " + "frequency unchanged\n", offset); + } + + BIOSLOG(bios, "0x%04X: Reg: 0x%08X, Config: 0x%02X, Freq: %d0kHz\n", + offset, reg, config, freq); + + setPLL(bios, reg, freq * 10); + + return len; +} + +static int +init_end_repeat(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_END_REPEAT opcode: 0x36 ('6') + * + * offset (8 bit): opcode + * + * Marks the end of the block for INIT_REPEAT to repeat + */ + + /* no iexec->execute check by design */ + + /* + * iexec->repeat flag necessary to go past INIT_END_REPEAT opcode when + * we're not in repeat mode + */ + if (iexec->repeat) + return 0; + + return 1; +} + +static int +init_copy(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_COPY opcode: 0x37 ('7') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): register + * offset + 5 (8 bit): shift + * offset + 6 (8 bit): srcmask + * offset + 7 (16 bit): CRTC port + * offset + 9 (8 bit): CRTC index + * offset + 10 (8 bit): mask + * + * Read index "CRTC index" on "CRTC port", AND with "mask", OR with + * (REGVAL("register") >> "shift" & "srcmask") and write-back to CRTC + * port + */ + + uint32_t reg = ROM32(bios->data[offset + 1]); + uint8_t shift = bios->data[offset + 5]; + uint8_t srcmask = bios->data[offset + 6]; + uint16_t crtcport = ROM16(bios->data[offset + 7]); + uint8_t crtcindex = bios->data[offset + 9]; + uint8_t mask = bios->data[offset + 10]; + uint32_t data; + uint8_t crtcdata; + + if (!iexec->execute) + return 11; + + BIOSLOG(bios, "0x%04X: Reg: 0x%08X, Shift: 0x%02X, SrcMask: 0x%02X, " + "Port: 0x%04X, Index: 0x%02X, Mask: 0x%02X\n", + offset, reg, shift, srcmask, crtcport, crtcindex, mask); + + data = bios_rd32(bios, reg); + + if (shift < 0x80) + data >>= shift; + else + data <<= (0x100 - shift); + + data &= srcmask; + + crtcdata = bios_idxprt_rd(bios, crtcport, crtcindex) & mask; + crtcdata |= (uint8_t)data; + bios_idxprt_wr(bios, crtcport, crtcindex, crtcdata); + + return 11; +} + +static int +init_not(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_NOT opcode: 0x38 ('8') + * + * offset (8 bit): opcode + * + * Invert the current execute / no-execute condition (i.e. "else") + */ + if (iexec->execute) + BIOSLOG(bios, "0x%04X: ------ Skipping following commands ------\n", offset); + else + BIOSLOG(bios, "0x%04X: ------ Executing following commands ------\n", offset); + + iexec->execute = !iexec->execute; + return 1; +} + +static int +init_io_flag_condition(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_IO_FLAG_CONDITION opcode: 0x39 ('9') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): condition number + * + * Check condition "condition number" in the IO flag condition table. + * If condition not met skip subsequent opcodes until condition is + * inverted (INIT_NOT), or we hit INIT_RESUME + */ + + uint8_t cond = bios->data[offset + 1]; + + if (!iexec->execute) + return 2; + + if (io_flag_condition_met(bios, offset, cond)) + BIOSLOG(bios, "0x%04X: Condition fulfilled -- continuing to execute\n", offset); + else { + BIOSLOG(bios, "0x%04X: Condition not fulfilled -- skipping following commands\n", offset); + iexec->execute = false; + } + + return 2; +} + +static int +init_dp_condition(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_DP_CONDITION opcode: 0x3A ('') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): "sub" opcode + * offset + 2 (8 bit): unknown + * + */ + + struct bit_displayport_encoder_table *dpe = NULL; + struct dcb_entry *dcb = bios->display.output; + struct drm_device *dev = bios->dev; + uint8_t cond = bios->data[offset + 1]; + int dummy; + + BIOSLOG(bios, "0x%04X: subop 0x%02X\n", offset, cond); + + if (!iexec->execute) + return 3; + + dpe = nouveau_bios_dp_table(dev, dcb, &dummy); + if (!dpe) { + NV_ERROR(dev, "0x%04X: INIT_3A: no encoder table!!\n", offset); + return 3; + } + + switch (cond) { + case 0: + { + struct dcb_connector_table_entry *ent = + &bios->dcb.connector.entry[dcb->connector]; + + if (ent->type != DCB_CONNECTOR_eDP) + iexec->execute = false; + } + break; + case 1: + case 2: + if (!(dpe->unknown & cond)) + iexec->execute = false; + break; + case 5: + { + struct nouveau_i2c_chan *auxch; + int ret; + + auxch = nouveau_i2c_find(dev, bios->display.output->i2c_index); + if (!auxch) { + NV_ERROR(dev, "0x%04X: couldn't get auxch\n", offset); + return 3; + } + + ret = nouveau_dp_auxch(auxch, 9, 0xd, &cond, 1); + if (ret) { + NV_ERROR(dev, "0x%04X: auxch rd fail: %d\n", offset, ret); + return 3; + } + + if (!(cond & 1)) + iexec->execute = false; + } + break; + default: + NV_WARN(dev, "0x%04X: unknown INIT_3A op: %d\n", offset, cond); + break; + } + + if (iexec->execute) + BIOSLOG(bios, "0x%04X: continuing to execute\n", offset); + else + BIOSLOG(bios, "0x%04X: skipping following commands\n", offset); + + return 3; +} + +static int +init_op_3b(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_3B opcode: 0x3B ('') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): crtc index + * + */ + + uint8_t or = ffs(bios->display.output->or) - 1; + uint8_t index = bios->data[offset + 1]; + uint8_t data; + + if (!iexec->execute) + return 2; + + data = bios_idxprt_rd(bios, 0x3d4, index); + bios_idxprt_wr(bios, 0x3d4, index, data & ~(1 << or)); + return 2; +} + +static int +init_op_3c(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_3C opcode: 0x3C ('') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): crtc index + * + */ + + uint8_t or = ffs(bios->display.output->or) - 1; + uint8_t index = bios->data[offset + 1]; + uint8_t data; + + if (!iexec->execute) + return 2; + + data = bios_idxprt_rd(bios, 0x3d4, index); + bios_idxprt_wr(bios, 0x3d4, index, data | (1 << or)); + return 2; +} + +static int +init_idx_addr_latched(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_INDEX_ADDRESS_LATCHED opcode: 0x49 ('I') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): control register + * offset + 5 (32 bit): data register + * offset + 9 (32 bit): mask + * offset + 13 (32 bit): data + * offset + 17 (8 bit): count + * offset + 18 (8 bit): address 1 + * offset + 19 (8 bit): data 1 + * ... + * + * For each of "count" address and data pairs, write "data n" to + * "data register", read the current value of "control register", + * and write it back once ANDed with "mask", ORed with "data", + * and ORed with "address n" + */ + + uint32_t controlreg = ROM32(bios->data[offset + 1]); + uint32_t datareg = ROM32(bios->data[offset + 5]); + uint32_t mask = ROM32(bios->data[offset + 9]); + uint32_t data = ROM32(bios->data[offset + 13]); + uint8_t count = bios->data[offset + 17]; + int len = 18 + count * 2; + uint32_t value; + int i; + + if (!iexec->execute) + return len; + + BIOSLOG(bios, "0x%04X: ControlReg: 0x%08X, DataReg: 0x%08X, " + "Mask: 0x%08X, Data: 0x%08X, Count: 0x%02X\n", + offset, controlreg, datareg, mask, data, count); + + for (i = 0; i < count; i++) { + uint8_t instaddress = bios->data[offset + 18 + i * 2]; + uint8_t instdata = bios->data[offset + 19 + i * 2]; + + BIOSLOG(bios, "0x%04X: Address: 0x%02X, Data: 0x%02X\n", + offset, instaddress, instdata); + + bios_wr32(bios, datareg, instdata); + value = bios_rd32(bios, controlreg) & mask; + value |= data; + value |= instaddress; + bios_wr32(bios, controlreg, value); + } + + return len; +} + +static int +init_io_restrict_pll2(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_IO_RESTRICT_PLL2 opcode: 0x4A ('J') + * + * offset (8 bit): opcode + * offset + 1 (16 bit): CRTC port + * offset + 3 (8 bit): CRTC index + * offset + 4 (8 bit): mask + * offset + 5 (8 bit): shift + * offset + 6 (8 bit): count + * offset + 7 (32 bit): register + * offset + 11 (32 bit): frequency 1 + * ... + * + * Starting at offset + 11 there are "count" 32 bit frequencies (kHz). + * Set PLL register "register" to coefficients for frequency n, + * selected by reading index "CRTC index" of "CRTC port" ANDed with + * "mask" and shifted right by "shift". + */ + + uint16_t crtcport = ROM16(bios->data[offset + 1]); + uint8_t crtcindex = bios->data[offset + 3]; + uint8_t mask = bios->data[offset + 4]; + uint8_t shift = bios->data[offset + 5]; + uint8_t count = bios->data[offset + 6]; + uint32_t reg = ROM32(bios->data[offset + 7]); + int len = 11 + count * 4; + uint8_t config; + uint32_t freq; + + if (!iexec->execute) + return len; + + BIOSLOG(bios, "0x%04X: Port: 0x%04X, Index: 0x%02X, Mask: 0x%02X, " + "Shift: 0x%02X, Count: 0x%02X, Reg: 0x%08X\n", + offset, crtcport, crtcindex, mask, shift, count, reg); + + if (!reg) + return len; + + config = (bios_idxprt_rd(bios, crtcport, crtcindex) & mask) >> shift; + if (config > count) { + NV_ERROR(bios->dev, + "0x%04X: Config 0x%02X exceeds maximal bound 0x%02X\n", + offset, config, count); + return len; + } + + freq = ROM32(bios->data[offset + 11 + config * 4]); + + BIOSLOG(bios, "0x%04X: Reg: 0x%08X, Config: 0x%02X, Freq: %dkHz\n", + offset, reg, config, freq); + + setPLL(bios, reg, freq); + + return len; +} + +static int +init_pll2(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_PLL2 opcode: 0x4B ('K') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): register + * offset + 5 (32 bit): freq + * + * Set PLL register "register" to coefficients for frequency "freq" + */ + + uint32_t reg = ROM32(bios->data[offset + 1]); + uint32_t freq = ROM32(bios->data[offset + 5]); + + if (!iexec->execute) + return 9; + + BIOSLOG(bios, "0x%04X: Reg: 0x%04X, Freq: %dkHz\n", + offset, reg, freq); + + setPLL(bios, reg, freq); + return 9; +} + +static int +init_i2c_byte(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_I2C_BYTE opcode: 0x4C ('L') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): DCB I2C table entry index + * offset + 2 (8 bit): I2C slave address + * offset + 3 (8 bit): count + * offset + 4 (8 bit): I2C register 1 + * offset + 5 (8 bit): mask 1 + * offset + 6 (8 bit): data 1 + * ... + * + * For each of "count" registers given by "I2C register n" on the device + * addressed by "I2C slave address" on the I2C bus given by + * "DCB I2C table entry index", read the register, AND the result with + * "mask n" and OR it with "data n" before writing it back to the device + */ + + struct drm_device *dev = bios->dev; + uint8_t i2c_index = bios->data[offset + 1]; + uint8_t i2c_address = bios->data[offset + 2] >> 1; + uint8_t count = bios->data[offset + 3]; + struct nouveau_i2c_chan *chan; + int len = 4 + count * 3; + int ret, i; + + if (!iexec->execute) + return len; + + BIOSLOG(bios, "0x%04X: DCBI2CIndex: 0x%02X, I2CAddress: 0x%02X, " + "Count: 0x%02X\n", + offset, i2c_index, i2c_address, count); + + chan = init_i2c_device_find(dev, i2c_index); + if (!chan) { + NV_ERROR(dev, "0x%04X: i2c bus not found\n", offset); + return len; + } + + for (i = 0; i < count; i++) { + uint8_t reg = bios->data[offset + 4 + i * 3]; + uint8_t mask = bios->data[offset + 5 + i * 3]; + uint8_t data = bios->data[offset + 6 + i * 3]; + union i2c_smbus_data val; + + ret = i2c_smbus_xfer(&chan->adapter, i2c_address, 0, + I2C_SMBUS_READ, reg, + I2C_SMBUS_BYTE_DATA, &val); + if (ret < 0) { + NV_ERROR(dev, "0x%04X: i2c rd fail: %d\n", offset, ret); + return len; + } + + BIOSLOG(bios, "0x%04X: I2CReg: 0x%02X, Value: 0x%02X, " + "Mask: 0x%02X, Data: 0x%02X\n", + offset, reg, val.byte, mask, data); + + if (!bios->execute) + continue; + + val.byte &= mask; + val.byte |= data; + ret = i2c_smbus_xfer(&chan->adapter, i2c_address, 0, + I2C_SMBUS_WRITE, reg, + I2C_SMBUS_BYTE_DATA, &val); + if (ret < 0) { + NV_ERROR(dev, "0x%04X: i2c wr fail: %d\n", offset, ret); + return len; + } + } + + return len; +} + +static int +init_zm_i2c_byte(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_ZM_I2C_BYTE opcode: 0x4D ('M') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): DCB I2C table entry index + * offset + 2 (8 bit): I2C slave address + * offset + 3 (8 bit): count + * offset + 4 (8 bit): I2C register 1 + * offset + 5 (8 bit): data 1 + * ... + * + * For each of "count" registers given by "I2C register n" on the device + * addressed by "I2C slave address" on the I2C bus given by + * "DCB I2C table entry index", set the register to "data n" + */ + + struct drm_device *dev = bios->dev; + uint8_t i2c_index = bios->data[offset + 1]; + uint8_t i2c_address = bios->data[offset + 2] >> 1; + uint8_t count = bios->data[offset + 3]; + struct nouveau_i2c_chan *chan; + int len = 4 + count * 2; + int ret, i; + + if (!iexec->execute) + return len; + + BIOSLOG(bios, "0x%04X: DCBI2CIndex: 0x%02X, I2CAddress: 0x%02X, " + "Count: 0x%02X\n", + offset, i2c_index, i2c_address, count); + + chan = init_i2c_device_find(dev, i2c_index); + if (!chan) { + NV_ERROR(dev, "0x%04X: i2c bus not found\n", offset); + return len; + } + + for (i = 0; i < count; i++) { + uint8_t reg = bios->data[offset + 4 + i * 2]; + union i2c_smbus_data val; + + val.byte = bios->data[offset + 5 + i * 2]; + + BIOSLOG(bios, "0x%04X: I2CReg: 0x%02X, Data: 0x%02X\n", + offset, reg, val.byte); + + if (!bios->execute) + continue; + + ret = i2c_smbus_xfer(&chan->adapter, i2c_address, 0, + I2C_SMBUS_WRITE, reg, + I2C_SMBUS_BYTE_DATA, &val); + if (ret < 0) { + NV_ERROR(dev, "0x%04X: i2c wr fail: %d\n", offset, ret); + return len; + } + } + + return len; +} + +static int +init_zm_i2c(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_ZM_I2C opcode: 0x4E ('N') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): DCB I2C table entry index + * offset + 2 (8 bit): I2C slave address + * offset + 3 (8 bit): count + * offset + 4 (8 bit): data 1 + * ... + * + * Send "count" bytes ("data n") to the device addressed by "I2C slave + * address" on the I2C bus given by "DCB I2C table entry index" + */ + + struct drm_device *dev = bios->dev; + uint8_t i2c_index = bios->data[offset + 1]; + uint8_t i2c_address = bios->data[offset + 2] >> 1; + uint8_t count = bios->data[offset + 3]; + int len = 4 + count; + struct nouveau_i2c_chan *chan; + struct i2c_msg msg; + uint8_t data[256]; + int ret, i; + + if (!iexec->execute) + return len; + + BIOSLOG(bios, "0x%04X: DCBI2CIndex: 0x%02X, I2CAddress: 0x%02X, " + "Count: 0x%02X\n", + offset, i2c_index, i2c_address, count); + + chan = init_i2c_device_find(dev, i2c_index); + if (!chan) { + NV_ERROR(dev, "0x%04X: i2c bus not found\n", offset); + return len; + } + + for (i = 0; i < count; i++) { + data[i] = bios->data[offset + 4 + i]; + + BIOSLOG(bios, "0x%04X: Data: 0x%02X\n", offset, data[i]); + } + + if (bios->execute) { + msg.addr = i2c_address; + msg.flags = 0; + msg.len = count; + msg.buf = data; + ret = i2c_transfer(&chan->adapter, &msg, 1); + if (ret != 1) { + NV_ERROR(dev, "0x%04X: i2c wr fail: %d\n", offset, ret); + return len; + } + } + + return len; +} + +static int +init_tmds(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_TMDS opcode: 0x4F ('O') (non-canon name) + * + * offset (8 bit): opcode + * offset + 1 (8 bit): magic lookup value + * offset + 2 (8 bit): TMDS address + * offset + 3 (8 bit): mask + * offset + 4 (8 bit): data + * + * Read the data reg for TMDS address "TMDS address", AND it with mask + * and OR it with data, then write it back + * "magic lookup value" determines which TMDS base address register is + * used -- see get_tmds_index_reg() + */ + + struct drm_device *dev = bios->dev; + uint8_t mlv = bios->data[offset + 1]; + uint32_t tmdsaddr = bios->data[offset + 2]; + uint8_t mask = bios->data[offset + 3]; + uint8_t data = bios->data[offset + 4]; + uint32_t reg, value; + + if (!iexec->execute) + return 5; + + BIOSLOG(bios, "0x%04X: MagicLookupValue: 0x%02X, TMDSAddr: 0x%02X, " + "Mask: 0x%02X, Data: 0x%02X\n", + offset, mlv, tmdsaddr, mask, data); + + reg = get_tmds_index_reg(bios->dev, mlv); + if (!reg) { + NV_ERROR(dev, "0x%04X: no tmds_index_reg\n", offset); + return 5; + } + + bios_wr32(bios, reg, + tmdsaddr | NV_PRAMDAC_FP_TMDS_CONTROL_WRITE_DISABLE); + value = (bios_rd32(bios, reg + 4) & mask) | data; + bios_wr32(bios, reg + 4, value); + bios_wr32(bios, reg, tmdsaddr); + + return 5; +} + +static int +init_zm_tmds_group(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_ZM_TMDS_GROUP opcode: 0x50 ('P') (non-canon name) + * + * offset (8 bit): opcode + * offset + 1 (8 bit): magic lookup value + * offset + 2 (8 bit): count + * offset + 3 (8 bit): addr 1 + * offset + 4 (8 bit): data 1 + * ... + * + * For each of "count" TMDS address and data pairs write "data n" to + * "addr n". "magic lookup value" determines which TMDS base address + * register is used -- see get_tmds_index_reg() + */ + + struct drm_device *dev = bios->dev; + uint8_t mlv = bios->data[offset + 1]; + uint8_t count = bios->data[offset + 2]; + int len = 3 + count * 2; + uint32_t reg; + int i; + + if (!iexec->execute) + return len; + + BIOSLOG(bios, "0x%04X: MagicLookupValue: 0x%02X, Count: 0x%02X\n", + offset, mlv, count); + + reg = get_tmds_index_reg(bios->dev, mlv); + if (!reg) { + NV_ERROR(dev, "0x%04X: no tmds_index_reg\n", offset); + return len; + } + + for (i = 0; i < count; i++) { + uint8_t tmdsaddr = bios->data[offset + 3 + i * 2]; + uint8_t tmdsdata = bios->data[offset + 4 + i * 2]; + + bios_wr32(bios, reg + 4, tmdsdata); + bios_wr32(bios, reg, tmdsaddr); + } + + return len; +} + +static int +init_cr_idx_adr_latch(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_CR_INDEX_ADDRESS_LATCHED opcode: 0x51 ('Q') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): CRTC index1 + * offset + 2 (8 bit): CRTC index2 + * offset + 3 (8 bit): baseaddr + * offset + 4 (8 bit): count + * offset + 5 (8 bit): data 1 + * ... + * + * For each of "count" address and data pairs, write "baseaddr + n" to + * "CRTC index1" and "data n" to "CRTC index2" + * Once complete, restore initial value read from "CRTC index1" + */ + uint8_t crtcindex1 = bios->data[offset + 1]; + uint8_t crtcindex2 = bios->data[offset + 2]; + uint8_t baseaddr = bios->data[offset + 3]; + uint8_t count = bios->data[offset + 4]; + int len = 5 + count; + uint8_t oldaddr, data; + int i; + + if (!iexec->execute) + return len; + + BIOSLOG(bios, "0x%04X: Index1: 0x%02X, Index2: 0x%02X, " + "BaseAddr: 0x%02X, Count: 0x%02X\n", + offset, crtcindex1, crtcindex2, baseaddr, count); + + oldaddr = bios_idxprt_rd(bios, NV_CIO_CRX__COLOR, crtcindex1); + + for (i = 0; i < count; i++) { + bios_idxprt_wr(bios, NV_CIO_CRX__COLOR, crtcindex1, + baseaddr + i); + data = bios->data[offset + 5 + i]; + bios_idxprt_wr(bios, NV_CIO_CRX__COLOR, crtcindex2, data); + } + + bios_idxprt_wr(bios, NV_CIO_CRX__COLOR, crtcindex1, oldaddr); + + return len; +} + +static int +init_cr(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_CR opcode: 0x52 ('R') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): CRTC index + * offset + 2 (8 bit): mask + * offset + 3 (8 bit): data + * + * Assign the value of at "CRTC index" ANDed with mask and ORed with + * data back to "CRTC index" + */ + + uint8_t crtcindex = bios->data[offset + 1]; + uint8_t mask = bios->data[offset + 2]; + uint8_t data = bios->data[offset + 3]; + uint8_t value; + + if (!iexec->execute) + return 4; + + BIOSLOG(bios, "0x%04X: Index: 0x%02X, Mask: 0x%02X, Data: 0x%02X\n", + offset, crtcindex, mask, data); + + value = bios_idxprt_rd(bios, NV_CIO_CRX__COLOR, crtcindex) & mask; + value |= data; + bios_idxprt_wr(bios, NV_CIO_CRX__COLOR, crtcindex, value); + + return 4; +} + +static int +init_zm_cr(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_ZM_CR opcode: 0x53 ('S') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): CRTC index + * offset + 2 (8 bit): value + * + * Assign "value" to CRTC register with index "CRTC index". + */ + + uint8_t crtcindex = ROM32(bios->data[offset + 1]); + uint8_t data = bios->data[offset + 2]; + + if (!iexec->execute) + return 3; + + bios_idxprt_wr(bios, NV_CIO_CRX__COLOR, crtcindex, data); + + return 3; +} + +static int +init_zm_cr_group(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_ZM_CR_GROUP opcode: 0x54 ('T') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): count + * offset + 2 (8 bit): CRTC index 1 + * offset + 3 (8 bit): value 1 + * ... + * + * For "count", assign "value n" to CRTC register with index + * "CRTC index n". + */ + + uint8_t count = bios->data[offset + 1]; + int len = 2 + count * 2; + int i; + + if (!iexec->execute) + return len; + + for (i = 0; i < count; i++) + init_zm_cr(bios, offset + 2 + 2 * i - 1, iexec); + + return len; +} + +static int +init_condition_time(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_CONDITION_TIME opcode: 0x56 ('V') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): condition number + * offset + 2 (8 bit): retries / 50 + * + * Check condition "condition number" in the condition table. + * Bios code then sleeps for 2ms if the condition is not met, and + * repeats up to "retries" times, but on one C51 this has proved + * insufficient. In mmiotraces the driver sleeps for 20ms, so we do + * this, and bail after "retries" times, or 2s, whichever is less. + * If still not met after retries, clear execution flag for this table. + */ + + uint8_t cond = bios->data[offset + 1]; + uint16_t retries = bios->data[offset + 2] * 50; + unsigned cnt; + + if (!iexec->execute) + return 3; + + if (retries > 100) + retries = 100; + + BIOSLOG(bios, "0x%04X: Condition: 0x%02X, Retries: 0x%02X\n", + offset, cond, retries); + + if (!bios->execute) /* avoid 2s delays when "faking" execution */ + retries = 1; + + for (cnt = 0; cnt < retries; cnt++) { + if (bios_condition_met(bios, offset, cond)) { + BIOSLOG(bios, "0x%04X: Condition met, continuing\n", + offset); + break; + } else { + BIOSLOG(bios, "0x%04X: " + "Condition not met, sleeping for 20ms\n", + offset); + msleep(20); + } + } + + if (!bios_condition_met(bios, offset, cond)) { + NV_WARN(bios->dev, + "0x%04X: Condition still not met after %dms, " + "skipping following opcodes\n", offset, 20 * retries); + iexec->execute = false; + } + + return 3; +} + +static int +init_ltime(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_LTIME opcode: 0x57 ('V') + * + * offset (8 bit): opcode + * offset + 1 (16 bit): time + * + * Sleep for "time" miliseconds. + */ + + unsigned time = ROM16(bios->data[offset + 1]); + + if (!iexec->execute) + return 3; + + BIOSLOG(bios, "0x%04X: Sleeping for 0x%04X miliseconds\n", + offset, time); + + msleep(time); + + return 3; +} + +static int +init_zm_reg_sequence(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_ZM_REG_SEQUENCE opcode: 0x58 ('X') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): base register + * offset + 5 (8 bit): count + * offset + 6 (32 bit): value 1 + * ... + * + * Starting at offset + 6 there are "count" 32 bit values. + * For "count" iterations set "base register" + 4 * current_iteration + * to "value current_iteration" + */ + + uint32_t basereg = ROM32(bios->data[offset + 1]); + uint32_t count = bios->data[offset + 5]; + int len = 6 + count * 4; + int i; + + if (!iexec->execute) + return len; + + BIOSLOG(bios, "0x%04X: BaseReg: 0x%08X, Count: 0x%02X\n", + offset, basereg, count); + + for (i = 0; i < count; i++) { + uint32_t reg = basereg + i * 4; + uint32_t data = ROM32(bios->data[offset + 6 + i * 4]); + + bios_wr32(bios, reg, data); + } + + return len; +} + +static int +init_sub_direct(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_SUB_DIRECT opcode: 0x5B ('[') + * + * offset (8 bit): opcode + * offset + 1 (16 bit): subroutine offset (in bios) + * + * Calls a subroutine that will execute commands until INIT_DONE + * is found. + */ + + uint16_t sub_offset = ROM16(bios->data[offset + 1]); + + if (!iexec->execute) + return 3; + + BIOSLOG(bios, "0x%04X: Executing subroutine at 0x%04X\n", + offset, sub_offset); + + parse_init_table(bios, sub_offset, iexec); + + BIOSLOG(bios, "0x%04X: End of 0x%04X subroutine\n", offset, sub_offset); + + return 3; +} + +static int +init_i2c_if(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_I2C_IF opcode: 0x5E ('^') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): DCB I2C table entry index + * offset + 2 (8 bit): I2C slave address + * offset + 3 (8 bit): I2C register + * offset + 4 (8 bit): mask + * offset + 5 (8 bit): data + * + * Read the register given by "I2C register" on the device addressed + * by "I2C slave address" on the I2C bus given by "DCB I2C table + * entry index". Compare the result AND "mask" to "data". + * If they're not equal, skip subsequent opcodes until condition is + * inverted (INIT_NOT), or we hit INIT_RESUME + */ + + uint8_t i2c_index = bios->data[offset + 1]; + uint8_t i2c_address = bios->data[offset + 2] >> 1; + uint8_t reg = bios->data[offset + 3]; + uint8_t mask = bios->data[offset + 4]; + uint8_t data = bios->data[offset + 5]; + struct nouveau_i2c_chan *chan; + union i2c_smbus_data val; + int ret; + + /* no execute check by design */ + + BIOSLOG(bios, "0x%04X: DCBI2CIndex: 0x%02X, I2CAddress: 0x%02X\n", + offset, i2c_index, i2c_address); + + chan = init_i2c_device_find(bios->dev, i2c_index); + if (!chan) + return -ENODEV; + + ret = i2c_smbus_xfer(&chan->adapter, i2c_address, 0, + I2C_SMBUS_READ, reg, + I2C_SMBUS_BYTE_DATA, &val); + if (ret < 0) { + BIOSLOG(bios, "0x%04X: I2CReg: 0x%02X, Value: [no device], " + "Mask: 0x%02X, Data: 0x%02X\n", + offset, reg, mask, data); + iexec->execute = 0; + return 6; + } + + BIOSLOG(bios, "0x%04X: I2CReg: 0x%02X, Value: 0x%02X, " + "Mask: 0x%02X, Data: 0x%02X\n", + offset, reg, val.byte, mask, data); + + iexec->execute = ((val.byte & mask) == data); + + return 6; +} + +static int +init_copy_nv_reg(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_COPY_NV_REG opcode: 0x5F ('_') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): src reg + * offset + 5 (8 bit): shift + * offset + 6 (32 bit): src mask + * offset + 10 (32 bit): xor + * offset + 14 (32 bit): dst reg + * offset + 18 (32 bit): dst mask + * + * Shift REGVAL("src reg") right by (signed) "shift", AND result with + * "src mask", then XOR with "xor". Write this OR'd with + * (REGVAL("dst reg") AND'd with "dst mask") to "dst reg" + */ + + uint32_t srcreg = *((uint32_t *)(&bios->data[offset + 1])); + uint8_t shift = bios->data[offset + 5]; + uint32_t srcmask = *((uint32_t *)(&bios->data[offset + 6])); + uint32_t xor = *((uint32_t *)(&bios->data[offset + 10])); + uint32_t dstreg = *((uint32_t *)(&bios->data[offset + 14])); + uint32_t dstmask = *((uint32_t *)(&bios->data[offset + 18])); + uint32_t srcvalue, dstvalue; + + if (!iexec->execute) + return 22; + + BIOSLOG(bios, "0x%04X: SrcReg: 0x%08X, Shift: 0x%02X, SrcMask: 0x%08X, " + "Xor: 0x%08X, DstReg: 0x%08X, DstMask: 0x%08X\n", + offset, srcreg, shift, srcmask, xor, dstreg, dstmask); + + srcvalue = bios_rd32(bios, srcreg); + + if (shift < 0x80) + srcvalue >>= shift; + else + srcvalue <<= (0x100 - shift); + + srcvalue = (srcvalue & srcmask) ^ xor; + + dstvalue = bios_rd32(bios, dstreg) & dstmask; + + bios_wr32(bios, dstreg, dstvalue | srcvalue); + + return 22; +} + +static int +init_zm_index_io(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_ZM_INDEX_IO opcode: 0x62 ('b') + * + * offset (8 bit): opcode + * offset + 1 (16 bit): CRTC port + * offset + 3 (8 bit): CRTC index + * offset + 4 (8 bit): data + * + * Write "data" to index "CRTC index" of "CRTC port" + */ + uint16_t crtcport = ROM16(bios->data[offset + 1]); + uint8_t crtcindex = bios->data[offset + 3]; + uint8_t data = bios->data[offset + 4]; + + if (!iexec->execute) + return 5; + + bios_idxprt_wr(bios, crtcport, crtcindex, data); + + return 5; +} + +static inline void +bios_md32(struct nvbios *bios, uint32_t reg, + uint32_t mask, uint32_t val) +{ + bios_wr32(bios, reg, (bios_rd32(bios, reg) & ~mask) | val); +} + +static uint32_t +peek_fb(struct drm_device *dev, struct io_mapping *fb, + uint32_t off) +{ + uint32_t val = 0; + + if (off < pci_resource_len(dev->pdev, 1)) { +#ifdef PSCNV_KAPI_IO_MAPPING_3 + uint8_t __iomem *p = + io_mapping_map_atomic_wc(fb, off & PAGE_MASK, KM_USER0); +#else + uint8_t __iomem *p = + io_mapping_map_atomic_wc(fb, off & PAGE_MASK); +#endif + + val = ioread32(p + (off & ~PAGE_MASK)); + +#ifdef PSCNV_KAPI_IO_MAPPING_3 + io_mapping_unmap_atomic(p, KM_USER0); +#else + io_mapping_unmap_atomic(p); +#endif + + } + + return val; +} + +static void +poke_fb(struct drm_device *dev, struct io_mapping *fb, + uint32_t off, uint32_t val) +{ + if (off < pci_resource_len(dev->pdev, 1)) { +#ifdef PSCNV_KAPI_IO_MAPPING_3 + uint8_t __iomem *p = + io_mapping_map_atomic_wc(fb, off & PAGE_MASK, KM_USER0); +#else + uint8_t __iomem *p = + io_mapping_map_atomic_wc(fb, off & PAGE_MASK); +#endif + + iowrite32(val, p + (off & ~PAGE_MASK)); + wmb(); + +#ifdef PSCNV_KAPI_IO_MAPPING_3 + io_mapping_unmap_atomic(p, KM_USER0); +#else + io_mapping_unmap_atomic(p); +#endif + } +} + +static inline bool +read_back_fb(struct drm_device *dev, struct io_mapping *fb, + uint32_t off, uint32_t val) +{ + poke_fb(dev, fb, off, val); + return val == peek_fb(dev, fb, off); +} + +static int +nv04_init_compute_mem(struct nvbios *bios) +{ + struct drm_device *dev = bios->dev; + uint32_t patt = 0xdeadbeef; + struct io_mapping *fb; + int i; + + /* Map the framebuffer aperture */ + fb = io_mapping_create_wc(pci_resource_start(dev->pdev, 1), + pci_resource_len(dev->pdev, 1)); + if (!fb) + return -ENOMEM; + + /* Sequencer and refresh off */ + NVWriteVgaSeq(dev, 0, 1, NVReadVgaSeq(dev, 0, 1) | 0x20); + bios_md32(bios, NV04_PFB_DEBUG_0, 0, NV04_PFB_DEBUG_0_REFRESH_OFF); + + bios_md32(bios, NV04_PFB_BOOT_0, ~0, + NV04_PFB_BOOT_0_RAM_AMOUNT_16MB | + NV04_PFB_BOOT_0_RAM_WIDTH_128 | + NV04_PFB_BOOT_0_RAM_TYPE_SGRAM_16MBIT); + + for (i = 0; i < 4; i++) + poke_fb(dev, fb, 4 * i, patt); + + poke_fb(dev, fb, 0x400000, patt + 1); + + if (peek_fb(dev, fb, 0) == patt + 1) { + bios_md32(bios, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_TYPE, + NV04_PFB_BOOT_0_RAM_TYPE_SDRAM_16MBIT); + bios_md32(bios, NV04_PFB_DEBUG_0, + NV04_PFB_DEBUG_0_REFRESH_OFF, 0); + + for (i = 0; i < 4; i++) + poke_fb(dev, fb, 4 * i, patt); + + if ((peek_fb(dev, fb, 0xc) & 0xffff) != (patt & 0xffff)) + bios_md32(bios, NV04_PFB_BOOT_0, + NV04_PFB_BOOT_0_RAM_WIDTH_128 | + NV04_PFB_BOOT_0_RAM_AMOUNT, + NV04_PFB_BOOT_0_RAM_AMOUNT_8MB); + + } else if ((peek_fb(dev, fb, 0xc) & 0xffff0000) != + (patt & 0xffff0000)) { + bios_md32(bios, NV04_PFB_BOOT_0, + NV04_PFB_BOOT_0_RAM_WIDTH_128 | + NV04_PFB_BOOT_0_RAM_AMOUNT, + NV04_PFB_BOOT_0_RAM_AMOUNT_4MB); + + } else if (peek_fb(dev, fb, 0) != patt) { + if (read_back_fb(dev, fb, 0x800000, patt)) + bios_md32(bios, NV04_PFB_BOOT_0, + NV04_PFB_BOOT_0_RAM_AMOUNT, + NV04_PFB_BOOT_0_RAM_AMOUNT_8MB); + else + bios_md32(bios, NV04_PFB_BOOT_0, + NV04_PFB_BOOT_0_RAM_AMOUNT, + NV04_PFB_BOOT_0_RAM_AMOUNT_4MB); + + bios_md32(bios, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_TYPE, + NV04_PFB_BOOT_0_RAM_TYPE_SGRAM_8MBIT); + + } else if (!read_back_fb(dev, fb, 0x800000, patt)) { + bios_md32(bios, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_AMOUNT, + NV04_PFB_BOOT_0_RAM_AMOUNT_8MB); + + } + + /* Refresh on, sequencer on */ + bios_md32(bios, NV04_PFB_DEBUG_0, NV04_PFB_DEBUG_0_REFRESH_OFF, 0); + NVWriteVgaSeq(dev, 0, 1, NVReadVgaSeq(dev, 0, 1) & ~0x20); + + io_mapping_free(fb); + return 0; +} + +static const uint8_t * +nv05_memory_config(struct nvbios *bios) +{ + /* Defaults for BIOSes lacking a memory config table */ + static const uint8_t default_config_tab[][2] = { + { 0x24, 0x00 }, + { 0x28, 0x00 }, + { 0x24, 0x01 }, + { 0x1f, 0x00 }, + { 0x0f, 0x00 }, + { 0x17, 0x00 }, + { 0x06, 0x00 }, + { 0x00, 0x00 } + }; + int i = (bios_rd32(bios, NV_PEXTDEV_BOOT_0) & + NV_PEXTDEV_BOOT_0_RAMCFG) >> 2; + + if (bios->legacy.mem_init_tbl_ptr) + return &bios->data[bios->legacy.mem_init_tbl_ptr + 2 * i]; + else + return default_config_tab[i]; +} + +static int +nv05_init_compute_mem(struct nvbios *bios) +{ + struct drm_device *dev = bios->dev; + const uint8_t *ramcfg = nv05_memory_config(bios); + uint32_t patt = 0xdeadbeef; + struct io_mapping *fb; + int i, v; + + /* Map the framebuffer aperture */ + fb = io_mapping_create_wc(pci_resource_start(dev->pdev, 1), + pci_resource_len(dev->pdev, 1)); + if (!fb) + return -ENOMEM; + + /* Sequencer off */ + NVWriteVgaSeq(dev, 0, 1, NVReadVgaSeq(dev, 0, 1) | 0x20); + + if (bios_rd32(bios, NV04_PFB_BOOT_0) & NV04_PFB_BOOT_0_UMA_ENABLE) + goto out; + + bios_md32(bios, NV04_PFB_DEBUG_0, NV04_PFB_DEBUG_0_REFRESH_OFF, 0); + + /* If present load the hardcoded scrambling table */ + if (bios->legacy.mem_init_tbl_ptr) { + uint32_t *scramble_tab = (uint32_t *)&bios->data[ + bios->legacy.mem_init_tbl_ptr + 0x10]; + + for (i = 0; i < 8; i++) + bios_wr32(bios, NV04_PFB_SCRAMBLE(i), + ROM32(scramble_tab[i])); + } + + /* Set memory type/width/length defaults depending on the straps */ + bios_md32(bios, NV04_PFB_BOOT_0, 0x3f, ramcfg[0]); + + if (ramcfg[1] & 0x80) + bios_md32(bios, NV04_PFB_CFG0, 0, NV04_PFB_CFG0_SCRAMBLE); + + bios_md32(bios, NV04_PFB_CFG1, 0x700001, (ramcfg[1] & 1) << 20); + bios_md32(bios, NV04_PFB_CFG1, 0, 1); + + /* Probe memory bus width */ + for (i = 0; i < 4; i++) + poke_fb(dev, fb, 4 * i, patt); + + if (peek_fb(dev, fb, 0xc) != patt) + bios_md32(bios, NV04_PFB_BOOT_0, + NV04_PFB_BOOT_0_RAM_WIDTH_128, 0); + + /* Probe memory length */ + v = bios_rd32(bios, NV04_PFB_BOOT_0) & NV04_PFB_BOOT_0_RAM_AMOUNT; + + if (v == NV04_PFB_BOOT_0_RAM_AMOUNT_32MB && + (!read_back_fb(dev, fb, 0x1000000, ++patt) || + !read_back_fb(dev, fb, 0, ++patt))) + bios_md32(bios, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_AMOUNT, + NV04_PFB_BOOT_0_RAM_AMOUNT_16MB); + + if (v == NV04_PFB_BOOT_0_RAM_AMOUNT_16MB && + !read_back_fb(dev, fb, 0x800000, ++patt)) + bios_md32(bios, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_AMOUNT, + NV04_PFB_BOOT_0_RAM_AMOUNT_8MB); + + if (!read_back_fb(dev, fb, 0x400000, ++patt)) + bios_md32(bios, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_AMOUNT, + NV04_PFB_BOOT_0_RAM_AMOUNT_4MB); + +out: + /* Sequencer on */ + NVWriteVgaSeq(dev, 0, 1, NVReadVgaSeq(dev, 0, 1) & ~0x20); + + io_mapping_free(fb); + return 0; +} + +static int +nv10_init_compute_mem(struct nvbios *bios) +{ + struct drm_device *dev = bios->dev; + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + const int mem_width[] = { 0x10, 0x00, 0x20 }; + const int mem_width_count = (dev_priv->chipset >= 0x17 ? 3 : 2); + uint32_t patt = 0xdeadbeef; + struct io_mapping *fb; + int i, j, k; + + /* Map the framebuffer aperture */ + fb = io_mapping_create_wc(pci_resource_start(dev->pdev, 1), + pci_resource_len(dev->pdev, 1)); + if (!fb) + return -ENOMEM; + + bios_wr32(bios, NV10_PFB_REFCTRL, NV10_PFB_REFCTRL_VALID_1); + + /* Probe memory bus width */ + for (i = 0; i < mem_width_count; i++) { + bios_md32(bios, NV04_PFB_CFG0, 0x30, mem_width[i]); + + for (j = 0; j < 4; j++) { + for (k = 0; k < 4; k++) + poke_fb(dev, fb, 0x1c, 0); + + poke_fb(dev, fb, 0x1c, patt); + poke_fb(dev, fb, 0x3c, 0); + + if (peek_fb(dev, fb, 0x1c) == patt) + goto mem_width_found; + } + } + +mem_width_found: + patt <<= 1; + + /* Probe amount of installed memory */ + for (i = 0; i < 4; i++) { + int off = bios_rd32(bios, NV04_PFB_FIFO_DATA) - 0x100000; + + poke_fb(dev, fb, off, patt); + poke_fb(dev, fb, 0, 0); + + peek_fb(dev, fb, 0); + peek_fb(dev, fb, 0); + peek_fb(dev, fb, 0); + peek_fb(dev, fb, 0); + + if (peek_fb(dev, fb, off) == patt) + goto amount_found; + } + + /* IC missing - disable the upper half memory space. */ + bios_md32(bios, NV04_PFB_CFG0, 0x1000, 0); + +amount_found: + io_mapping_free(fb); + return 0; +} + +static int +nv20_init_compute_mem(struct nvbios *bios) +{ + struct drm_device *dev = bios->dev; + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + uint32_t mask = (dev_priv->chipset >= 0x25 ? 0x300 : 0x900); + uint32_t amount, off; + struct io_mapping *fb; + + /* Map the framebuffer aperture */ + fb = io_mapping_create_wc(pci_resource_start(dev->pdev, 1), + pci_resource_len(dev->pdev, 1)); + if (!fb) + return -ENOMEM; + + bios_wr32(bios, NV10_PFB_REFCTRL, NV10_PFB_REFCTRL_VALID_1); + + /* Allow full addressing */ + bios_md32(bios, NV04_PFB_CFG0, 0, mask); + + amount = bios_rd32(bios, NV04_PFB_FIFO_DATA); + for (off = amount; off > 0x2000000; off -= 0x2000000) + poke_fb(dev, fb, off - 4, off); + + amount = bios_rd32(bios, NV04_PFB_FIFO_DATA); + if (amount != peek_fb(dev, fb, amount - 4)) + /* IC missing - disable the upper half memory space. */ + bios_md32(bios, NV04_PFB_CFG0, mask, 0); + + io_mapping_free(fb); + return 0; +} + +static int +init_compute_mem(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_COMPUTE_MEM opcode: 0x63 ('c') + * + * offset (8 bit): opcode + * + * This opcode is meant to set the PFB memory config registers + * appropriately so that we can correctly calculate how much VRAM it + * has (on nv10 and better chipsets the amount of installed VRAM is + * subsequently reported in NV_PFB_CSTATUS (0x10020C)). + * + * The implementation of this opcode in general consists of several + * parts: + * + * 1) Determination of memory type and density. Only necessary for + * really old chipsets, the memory type reported by the strap bits + * (0x101000) is assumed to be accurate on nv05 and newer. + * + * 2) Determination of the memory bus width. Usually done by a cunning + * combination of writes to offsets 0x1c and 0x3c in the fb, and + * seeing whether the written values are read back correctly. + * + * Only necessary on nv0x-nv1x and nv34, on the other cards we can + * trust the straps. + * + * 3) Determination of how many of the card's RAM pads have ICs + * attached, usually done by a cunning combination of writes to an + * offset slightly less than the maximum memory reported by + * NV_PFB_CSTATUS, then seeing if the test pattern can be read back. + * + * This appears to be a NOP on IGPs and NV4x or newer chipsets, both io + * logs of the VBIOS and kmmio traces of the binary driver POSTing the + * card show nothing being done for this opcode. Why is it still listed + * in the table?! + */ + + /* no iexec->execute check by design */ + + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + int ret; + + if (dev_priv->chipset >= 0x40 || + dev_priv->chipset == 0x1a || + dev_priv->chipset == 0x1f) + ret = 0; + else if (dev_priv->chipset >= 0x20 && + dev_priv->chipset != 0x34) + ret = nv20_init_compute_mem(bios); + else if (dev_priv->chipset >= 0x10) + ret = nv10_init_compute_mem(bios); + else if (dev_priv->chipset >= 0x5) + ret = nv05_init_compute_mem(bios); + else + ret = nv04_init_compute_mem(bios); + + if (ret) + return ret; + + return 1; +} + +static int +init_reset(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_RESET opcode: 0x65 ('e') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): register + * offset + 5 (32 bit): value1 + * offset + 9 (32 bit): value2 + * + * Assign "value1" to "register", then assign "value2" to "register" + */ + + uint32_t reg = ROM32(bios->data[offset + 1]); + uint32_t value1 = ROM32(bios->data[offset + 5]); + uint32_t value2 = ROM32(bios->data[offset + 9]); + uint32_t pci_nv_19, pci_nv_20; + + /* no iexec->execute check by design */ + + pci_nv_19 = bios_rd32(bios, NV_PBUS_PCI_NV_19); + bios_wr32(bios, NV_PBUS_PCI_NV_19, pci_nv_19 & ~0xf00); + + bios_wr32(bios, reg, value1); + + udelay(10); + + bios_wr32(bios, reg, value2); + bios_wr32(bios, NV_PBUS_PCI_NV_19, pci_nv_19); + + pci_nv_20 = bios_rd32(bios, NV_PBUS_PCI_NV_20); + pci_nv_20 &= ~NV_PBUS_PCI_NV_20_ROM_SHADOW_ENABLED; /* 0xfffffffe */ + bios_wr32(bios, NV_PBUS_PCI_NV_20, pci_nv_20); + + return 13; +} + +static int +init_configure_mem(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_CONFIGURE_MEM opcode: 0x66 ('f') + * + * offset (8 bit): opcode + * + * Equivalent to INIT_DONE on bios version 3 or greater. + * For early bios versions, sets up the memory registers, using values + * taken from the memory init table + */ + + /* no iexec->execute check by design */ + + uint16_t meminitoffs = bios->legacy.mem_init_tbl_ptr + MEM_INIT_SIZE * (bios_idxprt_rd(bios, NV_CIO_CRX__COLOR, NV_CIO_CRE_SCRATCH4__INDEX) >> 4); + uint16_t seqtbloffs = bios->legacy.sdr_seq_tbl_ptr, meminitdata = meminitoffs + 6; + uint32_t reg, data; + + if (bios->major_version > 2) + return 0; + + bios_idxprt_wr(bios, NV_VIO_SRX, NV_VIO_SR_CLOCK_INDEX, bios_idxprt_rd( + bios, NV_VIO_SRX, NV_VIO_SR_CLOCK_INDEX) | 0x20); + + if (bios->data[meminitoffs] & 1) + seqtbloffs = bios->legacy.ddr_seq_tbl_ptr; + + for (reg = ROM32(bios->data[seqtbloffs]); + reg != 0xffffffff; + reg = ROM32(bios->data[seqtbloffs += 4])) { + + switch (reg) { + case NV04_PFB_PRE: + data = NV04_PFB_PRE_CMD_PRECHARGE; + break; + case NV04_PFB_PAD: + data = NV04_PFB_PAD_CKE_NORMAL; + break; + case NV04_PFB_REF: + data = NV04_PFB_REF_CMD_REFRESH; + break; + default: + data = ROM32(bios->data[meminitdata]); + meminitdata += 4; + if (data == 0xffffffff) + continue; + } + + bios_wr32(bios, reg, data); + } + + return 1; +} + +static int +init_configure_clk(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_CONFIGURE_CLK opcode: 0x67 ('g') + * + * offset (8 bit): opcode + * + * Equivalent to INIT_DONE on bios version 3 or greater. + * For early bios versions, sets up the NVClk and MClk PLLs, using + * values taken from the memory init table + */ + + /* no iexec->execute check by design */ + + uint16_t meminitoffs = bios->legacy.mem_init_tbl_ptr + MEM_INIT_SIZE * (bios_idxprt_rd(bios, NV_CIO_CRX__COLOR, NV_CIO_CRE_SCRATCH4__INDEX) >> 4); + int clock; + + if (bios->major_version > 2) + return 0; + + clock = ROM16(bios->data[meminitoffs + 4]) * 10; + setPLL(bios, NV_PRAMDAC_NVPLL_COEFF, clock); + + clock = ROM16(bios->data[meminitoffs + 2]) * 10; + if (bios->data[meminitoffs] & 1) /* DDR */ + clock *= 2; + setPLL(bios, NV_PRAMDAC_MPLL_COEFF, clock); + + return 1; +} + +static int +init_configure_preinit(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_CONFIGURE_PREINIT opcode: 0x68 ('h') + * + * offset (8 bit): opcode + * + * Equivalent to INIT_DONE on bios version 3 or greater. + * For early bios versions, does early init, loading ram and crystal + * configuration from straps into CR3C + */ + + /* no iexec->execute check by design */ + + uint32_t straps = bios_rd32(bios, NV_PEXTDEV_BOOT_0); + uint8_t cr3c = ((straps << 2) & 0xf0) | (straps & 0x40) >> 6; + + if (bios->major_version > 2) + return 0; + + bios_idxprt_wr(bios, NV_CIO_CRX__COLOR, + NV_CIO_CRE_SCRATCH4__INDEX, cr3c); + + return 1; +} + +static int +init_io(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_IO opcode: 0x69 ('i') + * + * offset (8 bit): opcode + * offset + 1 (16 bit): CRTC port + * offset + 3 (8 bit): mask + * offset + 4 (8 bit): data + * + * Assign ((IOVAL("crtc port") & "mask") | "data") to "crtc port" + */ + + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + uint16_t crtcport = ROM16(bios->data[offset + 1]); + uint8_t mask = bios->data[offset + 3]; + uint8_t data = bios->data[offset + 4]; + + if (!iexec->execute) + return 5; + + BIOSLOG(bios, "0x%04X: Port: 0x%04X, Mask: 0x%02X, Data: 0x%02X\n", + offset, crtcport, mask, data); + + /* + * I have no idea what this does, but NVIDIA do this magic sequence + * in the places where this INIT_IO happens.. + */ + if (dev_priv->card_type >= NV_50 && crtcport == 0x3c3 && data == 1) { + int i; + + bios_wr32(bios, 0x614100, (bios_rd32( + bios, 0x614100) & 0x0fffffff) | 0x00800000); + + bios_wr32(bios, 0x00e18c, bios_rd32( + bios, 0x00e18c) | 0x00020000); + + bios_wr32(bios, 0x614900, (bios_rd32( + bios, 0x614900) & 0x0fffffff) | 0x00800000); + + bios_wr32(bios, 0x000200, bios_rd32( + bios, 0x000200) & ~0x40000000); + + mdelay(10); + + bios_wr32(bios, 0x00e18c, bios_rd32( + bios, 0x00e18c) & ~0x00020000); + + bios_wr32(bios, 0x000200, bios_rd32( + bios, 0x000200) | 0x40000000); + + bios_wr32(bios, 0x614100, 0x00800018); + bios_wr32(bios, 0x614900, 0x00800018); + + mdelay(10); + + bios_wr32(bios, 0x614100, 0x10000018); + bios_wr32(bios, 0x614900, 0x10000018); + + for (i = 0; i < 3; i++) + bios_wr32(bios, 0x614280 + (i*0x800), bios_rd32( + bios, 0x614280 + (i*0x800)) & 0xf0f0f0f0); + + for (i = 0; i < 2; i++) + bios_wr32(bios, 0x614300 + (i*0x800), bios_rd32( + bios, 0x614300 + (i*0x800)) & 0xfffff0f0); + + for (i = 0; i < 3; i++) + bios_wr32(bios, 0x614380 + (i*0x800), bios_rd32( + bios, 0x614380 + (i*0x800)) & 0xfffff0f0); + + for (i = 0; i < 2; i++) + bios_wr32(bios, 0x614200 + (i*0x800), bios_rd32( + bios, 0x614200 + (i*0x800)) & 0xfffffff0); + + for (i = 0; i < 2; i++) + bios_wr32(bios, 0x614108 + (i*0x800), bios_rd32( + bios, 0x614108 + (i*0x800)) & 0x0fffffff); + return 5; + } + + bios_port_wr(bios, crtcport, (bios_port_rd(bios, crtcport) & mask) | + data); + return 5; +} + +static int +init_sub(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_SUB opcode: 0x6B ('k') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): script number + * + * Execute script number "script number", as a subroutine + */ + + uint8_t sub = bios->data[offset + 1]; + + if (!iexec->execute) + return 2; + + BIOSLOG(bios, "0x%04X: Calling script %d\n", offset, sub); + + parse_init_table(bios, + ROM16(bios->data[bios->init_script_tbls_ptr + sub * 2]), + iexec); + + BIOSLOG(bios, "0x%04X: End of script %d\n", offset, sub); + + return 2; +} + +static int +init_ram_condition(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_RAM_CONDITION opcode: 0x6D ('m') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): mask + * offset + 2 (8 bit): cmpval + * + * Test if (NV04_PFB_BOOT_0 & "mask") equals "cmpval". + * If condition not met skip subsequent opcodes until condition is + * inverted (INIT_NOT), or we hit INIT_RESUME + */ + + uint8_t mask = bios->data[offset + 1]; + uint8_t cmpval = bios->data[offset + 2]; + uint8_t data; + + if (!iexec->execute) + return 3; + + data = bios_rd32(bios, NV04_PFB_BOOT_0) & mask; + + BIOSLOG(bios, "0x%04X: Checking if 0x%08X equals 0x%08X\n", + offset, data, cmpval); + + if (data == cmpval) + BIOSLOG(bios, "0x%04X: Condition fulfilled -- continuing to execute\n", offset); + else { + BIOSLOG(bios, "0x%04X: Condition not fulfilled -- skipping following commands\n", offset); + iexec->execute = false; + } + + return 3; +} + +static int +init_nv_reg(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_NV_REG opcode: 0x6E ('n') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): register + * offset + 5 (32 bit): mask + * offset + 9 (32 bit): data + * + * Assign ((REGVAL("register") & "mask") | "data") to "register" + */ + + uint32_t reg = ROM32(bios->data[offset + 1]); + uint32_t mask = ROM32(bios->data[offset + 5]); + uint32_t data = ROM32(bios->data[offset + 9]); + + if (!iexec->execute) + return 13; + + BIOSLOG(bios, "0x%04X: Reg: 0x%08X, Mask: 0x%08X, Data: 0x%08X\n", + offset, reg, mask, data); + + bios_wr32(bios, reg, (bios_rd32(bios, reg) & mask) | data); + + return 13; +} + +static int +init_macro(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_MACRO opcode: 0x6F ('o') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): macro number + * + * Look up macro index "macro number" in the macro index table. + * The macro index table entry has 1 byte for the index in the macro + * table, and 1 byte for the number of times to repeat the macro. + * The macro table entry has 4 bytes for the register address and + * 4 bytes for the value to write to that register + */ + + uint8_t macro_index_tbl_idx = bios->data[offset + 1]; + uint16_t tmp = bios->macro_index_tbl_ptr + (macro_index_tbl_idx * MACRO_INDEX_SIZE); + uint8_t macro_tbl_idx = bios->data[tmp]; + uint8_t count = bios->data[tmp + 1]; + uint32_t reg, data; + int i; + + if (!iexec->execute) + return 2; + + BIOSLOG(bios, "0x%04X: Macro: 0x%02X, MacroTableIndex: 0x%02X, " + "Count: 0x%02X\n", + offset, macro_index_tbl_idx, macro_tbl_idx, count); + + for (i = 0; i < count; i++) { + uint16_t macroentryptr = bios->macro_tbl_ptr + (macro_tbl_idx + i) * MACRO_SIZE; + + reg = ROM32(bios->data[macroentryptr]); + data = ROM32(bios->data[macroentryptr + 4]); + + bios_wr32(bios, reg, data); + } + + return 2; +} + +static int +init_done(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_DONE opcode: 0x71 ('q') + * + * offset (8 bit): opcode + * + * End the current script + */ + + /* mild retval abuse to stop parsing this table */ + return 0; +} + +static int +init_resume(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_RESUME opcode: 0x72 ('r') + * + * offset (8 bit): opcode + * + * End the current execute / no-execute condition + */ + + if (iexec->execute) + return 1; + + iexec->execute = true; + BIOSLOG(bios, "0x%04X: ---- Executing following commands ----\n", offset); + + return 1; +} + +static int +init_time(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_TIME opcode: 0x74 ('t') + * + * offset (8 bit): opcode + * offset + 1 (16 bit): time + * + * Sleep for "time" microseconds. + */ + + unsigned time = ROM16(bios->data[offset + 1]); + + if (!iexec->execute) + return 3; + + BIOSLOG(bios, "0x%04X: Sleeping for 0x%04X microseconds\n", + offset, time); + + if (time < 1000) + udelay(time); + else + msleep((time + 900) / 1000); + + return 3; +} + +static int +init_condition(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_CONDITION opcode: 0x75 ('u') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): condition number + * + * Check condition "condition number" in the condition table. + * If condition not met skip subsequent opcodes until condition is + * inverted (INIT_NOT), or we hit INIT_RESUME + */ + + uint8_t cond = bios->data[offset + 1]; + + if (!iexec->execute) + return 2; + + BIOSLOG(bios, "0x%04X: Condition: 0x%02X\n", offset, cond); + + if (bios_condition_met(bios, offset, cond)) + BIOSLOG(bios, "0x%04X: Condition fulfilled -- continuing to execute\n", offset); + else { + BIOSLOG(bios, "0x%04X: Condition not fulfilled -- skipping following commands\n", offset); + iexec->execute = false; + } + + return 2; +} + +static int +init_io_condition(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_IO_CONDITION opcode: 0x76 + * + * offset (8 bit): opcode + * offset + 1 (8 bit): condition number + * + * Check condition "condition number" in the io condition table. + * If condition not met skip subsequent opcodes until condition is + * inverted (INIT_NOT), or we hit INIT_RESUME + */ + + uint8_t cond = bios->data[offset + 1]; + + if (!iexec->execute) + return 2; + + BIOSLOG(bios, "0x%04X: IO condition: 0x%02X\n", offset, cond); + + if (io_condition_met(bios, offset, cond)) + BIOSLOG(bios, "0x%04X: Condition fulfilled -- continuing to execute\n", offset); + else { + BIOSLOG(bios, "0x%04X: Condition not fulfilled -- skipping following commands\n", offset); + iexec->execute = false; + } + + return 2; +} + +static int +init_index_io(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_INDEX_IO opcode: 0x78 ('x') + * + * offset (8 bit): opcode + * offset + 1 (16 bit): CRTC port + * offset + 3 (8 bit): CRTC index + * offset + 4 (8 bit): mask + * offset + 5 (8 bit): data + * + * Read value at index "CRTC index" on "CRTC port", AND with "mask", + * OR with "data", write-back + */ + + uint16_t crtcport = ROM16(bios->data[offset + 1]); + uint8_t crtcindex = bios->data[offset + 3]; + uint8_t mask = bios->data[offset + 4]; + uint8_t data = bios->data[offset + 5]; + uint8_t value; + + if (!iexec->execute) + return 6; + + BIOSLOG(bios, "0x%04X: Port: 0x%04X, Index: 0x%02X, Mask: 0x%02X, " + "Data: 0x%02X\n", + offset, crtcport, crtcindex, mask, data); + + value = (bios_idxprt_rd(bios, crtcport, crtcindex) & mask) | data; + bios_idxprt_wr(bios, crtcport, crtcindex, value); + + return 6; +} + +static int +init_pll(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_PLL opcode: 0x79 ('y') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): register + * offset + 5 (16 bit): freq + * + * Set PLL register "register" to coefficients for frequency (10kHz) + * "freq" + */ + + uint32_t reg = ROM32(bios->data[offset + 1]); + uint16_t freq = ROM16(bios->data[offset + 5]); + + if (!iexec->execute) + return 7; + + BIOSLOG(bios, "0x%04X: Reg: 0x%08X, Freq: %d0kHz\n", offset, reg, freq); + + setPLL(bios, reg, freq * 10); + + return 7; +} + +static int +init_zm_reg(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_ZM_REG opcode: 0x7A ('z') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): register + * offset + 5 (32 bit): value + * + * Assign "value" to "register" + */ + + uint32_t reg = ROM32(bios->data[offset + 1]); + uint32_t value = ROM32(bios->data[offset + 5]); + + if (!iexec->execute) + return 9; + + if (reg == 0x000200) + value |= 1; + + bios_wr32(bios, reg, value); + + return 9; +} + +static int +init_ram_restrict_pll(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_RAM_RESTRICT_PLL opcode: 0x87 ('') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): PLL type + * offset + 2 (32 bit): frequency 0 + * + * Uses the RAMCFG strap of PEXTDEV_BOOT as an index into the table at + * ram_restrict_table_ptr. The value read from there is used to select + * a frequency from the table starting at 'frequency 0' to be + * programmed into the PLL corresponding to 'type'. + * + * The PLL limits table on cards using this opcode has a mapping of + * 'type' to the relevant registers. + */ + + struct drm_device *dev = bios->dev; + uint32_t strap = (bios_rd32(bios, NV_PEXTDEV_BOOT_0) & 0x0000003c) >> 2; + uint8_t index = bios->data[bios->ram_restrict_tbl_ptr + strap]; + uint8_t type = bios->data[offset + 1]; + uint32_t freq = ROM32(bios->data[offset + 2 + (index * 4)]); + uint8_t *pll_limits = &bios->data[bios->pll_limit_tbl_ptr], *entry; + int len = 2 + bios->ram_restrict_group_count * 4; + int i; + + if (!iexec->execute) + return len; + + if (!bios->pll_limit_tbl_ptr || (pll_limits[0] & 0xf0) != 0x30) { + NV_ERROR(dev, "PLL limits table not version 3.x\n"); + return len; /* deliberate, allow default clocks to remain */ + } + + entry = pll_limits + pll_limits[1]; + for (i = 0; i < pll_limits[3]; i++, entry += pll_limits[2]) { + if (entry[0] == type) { + uint32_t reg = ROM32(entry[3]); + + BIOSLOG(bios, "0x%04X: " + "Type %02x Reg 0x%08x Freq %dKHz\n", + offset, type, reg, freq); + + setPLL(bios, reg, freq); + return len; + } + } + + NV_ERROR(dev, "PLL type 0x%02x not found in PLL limits table", type); + return len; +} + +static int +init_8c(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_8C opcode: 0x8C ('') + * + * NOP so far.... + * + */ + + return 1; +} + +static int +init_8d(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_8D opcode: 0x8D ('') + * + * NOP so far.... + * + */ + + return 1; +} + +static int +init_gpio(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_GPIO opcode: 0x8E ('') + * + * offset (8 bit): opcode + * + * Loop over all entries in the DCB GPIO table, and initialise + * each GPIO according to various values listed in each entry + */ + + struct drm_nouveau_private *dev_priv = bios->dev->dev_private; + struct nouveau_gpio_engine *pgpio = &dev_priv->engine.gpio; + const uint32_t nv50_gpio_ctl[2] = { 0xe100, 0xe28c }; + int i; + + if (dev_priv->card_type < NV_50) { + NV_ERROR(bios->dev, "INIT_GPIO on unsupported chipset\n"); + return 1; + } + + if (!iexec->execute) + return 1; + + for (i = 0; i < bios->dcb.gpio.entries; i++) { + struct dcb_gpio_entry *gpio = &bios->dcb.gpio.entry[i]; + uint32_t r, s, v; + + BIOSLOG(bios, "0x%04X: Entry: 0x%08X\n", offset, gpio->entry); + + BIOSLOG(bios, "0x%04X: set gpio 0x%02x, state %d\n", + offset, gpio->tag, gpio->state_default); + if (bios->execute) + pgpio->set(bios->dev, gpio->tag, gpio->state_default); + + /* The NVIDIA binary driver doesn't appear to actually do + * any of this, my VBIOS does however. + */ + /* Not a clue, needs de-magicing */ + r = nv50_gpio_ctl[gpio->line >> 4]; + s = (gpio->line & 0x0f); + v = bios_rd32(bios, r) & ~(0x00010001 << s); + switch ((gpio->entry & 0x06000000) >> 25) { + case 1: + v |= (0x00000001 << s); + break; + case 2: + v |= (0x00010000 << s); + break; + default: + break; + } + bios_wr32(bios, r, v); + } + + return 1; +} + +static int +init_ram_restrict_zm_reg_group(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_RAM_RESTRICT_ZM_REG_GROUP opcode: 0x8F ('') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): reg + * offset + 5 (8 bit): regincrement + * offset + 6 (8 bit): count + * offset + 7 (32 bit): value 1,1 + * ... + * + * Use the RAMCFG strap of PEXTDEV_BOOT as an index into the table at + * ram_restrict_table_ptr. The value read from here is 'n', and + * "value 1,n" gets written to "reg". This repeats "count" times and on + * each iteration 'm', "reg" increases by "regincrement" and + * "value m,n" is used. The extent of n is limited by a number read + * from the 'M' BIT table, herein called "blocklen" + */ + + uint32_t reg = ROM32(bios->data[offset + 1]); + uint8_t regincrement = bios->data[offset + 5]; + uint8_t count = bios->data[offset + 6]; + uint32_t strap_ramcfg, data; + /* previously set by 'M' BIT table */ + uint16_t blocklen = bios->ram_restrict_group_count * 4; + int len = 7 + count * blocklen; + uint8_t index; + int i; + + /* critical! to know the length of the opcode */; + if (!blocklen) { + NV_ERROR(bios->dev, + "0x%04X: Zero block length - has the M table " + "been parsed?\n", offset); + return -EINVAL; + } + + if (!iexec->execute) + return len; + + strap_ramcfg = (bios_rd32(bios, NV_PEXTDEV_BOOT_0) >> 2) & 0xf; + index = bios->data[bios->ram_restrict_tbl_ptr + strap_ramcfg]; + + BIOSLOG(bios, "0x%04X: Reg: 0x%08X, RegIncrement: 0x%02X, " + "Count: 0x%02X, StrapRamCfg: 0x%02X, Index: 0x%02X\n", + offset, reg, regincrement, count, strap_ramcfg, index); + + for (i = 0; i < count; i++) { + data = ROM32(bios->data[offset + 7 + index * 4 + blocklen * i]); + + bios_wr32(bios, reg, data); + + reg += regincrement; + } + + return len; +} + +static int +init_copy_zm_reg(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_COPY_ZM_REG opcode: 0x90 ('') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): src reg + * offset + 5 (32 bit): dst reg + * + * Put contents of "src reg" into "dst reg" + */ + + uint32_t srcreg = ROM32(bios->data[offset + 1]); + uint32_t dstreg = ROM32(bios->data[offset + 5]); + + if (!iexec->execute) + return 9; + + bios_wr32(bios, dstreg, bios_rd32(bios, srcreg)); + + return 9; +} + +static int +init_zm_reg_group_addr_latched(struct nvbios *bios, uint16_t offset, + struct init_exec *iexec) +{ + /* + * INIT_ZM_REG_GROUP_ADDRESS_LATCHED opcode: 0x91 ('') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): dst reg + * offset + 5 (8 bit): count + * offset + 6 (32 bit): data 1 + * ... + * + * For each of "count" values write "data n" to "dst reg" + */ + + uint32_t reg = ROM32(bios->data[offset + 1]); + uint8_t count = bios->data[offset + 5]; + int len = 6 + count * 4; + int i; + + if (!iexec->execute) + return len; + + for (i = 0; i < count; i++) { + uint32_t data = ROM32(bios->data[offset + 6 + 4 * i]); + bios_wr32(bios, reg, data); + } + + return len; +} + +static int +init_reserved(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_RESERVED opcode: 0x92 ('') + * + * offset (8 bit): opcode + * + * Seemingly does nothing + */ + + return 1; +} + +static int +init_96(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_96 opcode: 0x96 ('') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): sreg + * offset + 5 (8 bit): sshift + * offset + 6 (8 bit): smask + * offset + 7 (8 bit): index + * offset + 8 (32 bit): reg + * offset + 12 (32 bit): mask + * offset + 16 (8 bit): shift + * + */ + + uint16_t xlatptr = bios->init96_tbl_ptr + (bios->data[offset + 7] * 2); + uint32_t reg = ROM32(bios->data[offset + 8]); + uint32_t mask = ROM32(bios->data[offset + 12]); + uint32_t val; + + val = bios_rd32(bios, ROM32(bios->data[offset + 1])); + if (bios->data[offset + 5] < 0x80) + val >>= bios->data[offset + 5]; + else + val <<= (0x100 - bios->data[offset + 5]); + val &= bios->data[offset + 6]; + + val = bios->data[ROM16(bios->data[xlatptr]) + val]; + val <<= bios->data[offset + 16]; + + if (!iexec->execute) + return 17; + + bios_wr32(bios, reg, (bios_rd32(bios, reg) & mask) | val); + return 17; +} + +static int +init_97(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_97 opcode: 0x97 ('') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): register + * offset + 5 (32 bit): mask + * offset + 9 (32 bit): value + * + * Adds "value" to "register" preserving the fields specified + * by "mask" + */ + + uint32_t reg = ROM32(bios->data[offset + 1]); + uint32_t mask = ROM32(bios->data[offset + 5]); + uint32_t add = ROM32(bios->data[offset + 9]); + uint32_t val; + + val = bios_rd32(bios, reg); + val = (val & mask) | ((val + add) & ~mask); + + if (!iexec->execute) + return 13; + + bios_wr32(bios, reg, val); + return 13; +} + +static int +init_auxch(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_AUXCH opcode: 0x98 ('') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): address + * offset + 5 (8 bit): count + * offset + 6 (8 bit): mask 0 + * offset + 7 (8 bit): data 0 + * ... + * + */ + + struct drm_device *dev = bios->dev; + struct nouveau_i2c_chan *auxch; + uint32_t addr = ROM32(bios->data[offset + 1]); + uint8_t count = bios->data[offset + 5]; + int len = 6 + count * 2; + int ret, i; + + if (!bios->display.output) { + NV_ERROR(dev, "INIT_AUXCH: no active output\n"); + return len; + } + + auxch = init_i2c_device_find(dev, bios->display.output->i2c_index); + if (!auxch) { + NV_ERROR(dev, "INIT_AUXCH: couldn't get auxch %d\n", + bios->display.output->i2c_index); + return len; + } + + if (!iexec->execute) + return len; + + offset += 6; + for (i = 0; i < count; i++, offset += 2) { + uint8_t data; + + ret = nouveau_dp_auxch(auxch, 9, addr, &data, 1); + if (ret) { + NV_ERROR(dev, "INIT_AUXCH: rd auxch fail %d\n", ret); + return len; + } + + data &= bios->data[offset + 0]; + data |= bios->data[offset + 1]; + + ret = nouveau_dp_auxch(auxch, 8, addr, &data, 1); + if (ret) { + NV_ERROR(dev, "INIT_AUXCH: wr auxch fail %d\n", ret); + return len; + } + } + + return len; +} + +static int +init_zm_auxch(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_ZM_AUXCH opcode: 0x99 ('') + * + * offset (8 bit): opcode + * offset + 1 (32 bit): address + * offset + 5 (8 bit): count + * offset + 6 (8 bit): data 0 + * ... + * + */ + + struct drm_device *dev = bios->dev; + struct nouveau_i2c_chan *auxch; + uint32_t addr = ROM32(bios->data[offset + 1]); + uint8_t count = bios->data[offset + 5]; + int len = 6 + count; + int ret, i; + + if (!bios->display.output) { + NV_ERROR(dev, "INIT_ZM_AUXCH: no active output\n"); + return len; + } + + auxch = init_i2c_device_find(dev, bios->display.output->i2c_index); + if (!auxch) { + NV_ERROR(dev, "INIT_ZM_AUXCH: couldn't get auxch %d\n", + bios->display.output->i2c_index); + return len; + } + + if (!iexec->execute) + return len; + + offset += 6; + for (i = 0; i < count; i++, offset++) { + ret = nouveau_dp_auxch(auxch, 8, addr, &bios->data[offset], 1); + if (ret) { + NV_ERROR(dev, "INIT_ZM_AUXCH: wr auxch fail %d\n", ret); + return len; + } + } + + return len; +} + +static int +init_i2c_long_if(struct nvbios *bios, uint16_t offset, struct init_exec *iexec) +{ + /* + * INIT_I2C_LONG_IF opcode: 0x9A ('') + * + * offset (8 bit): opcode + * offset + 1 (8 bit): DCB I2C table entry index + * offset + 2 (8 bit): I2C slave address + * offset + 3 (16 bit): I2C register + * offset + 5 (8 bit): mask + * offset + 6 (8 bit): data + * + * Read the register given by "I2C register" on the device addressed + * by "I2C slave address" on the I2C bus given by "DCB I2C table + * entry index". Compare the result AND "mask" to "data". + * If they're not equal, skip subsequent opcodes until condition is + * inverted (INIT_NOT), or we hit INIT_RESUME + */ + + uint8_t i2c_index = bios->data[offset + 1]; + uint8_t i2c_address = bios->data[offset + 2] >> 1; + uint8_t reglo = bios->data[offset + 3]; + uint8_t reghi = bios->data[offset + 4]; + uint8_t mask = bios->data[offset + 5]; + uint8_t data = bios->data[offset + 6]; + struct nouveau_i2c_chan *chan; + uint8_t buf0[2] = { reghi, reglo }; + uint8_t buf1[1]; + struct i2c_msg msg[2] = { + { i2c_address, 0, 1, buf0 }, + { i2c_address, I2C_M_RD, 1, buf1 }, + }; + int ret; + + /* no execute check by design */ + + BIOSLOG(bios, "0x%04X: DCBI2CIndex: 0x%02X, I2CAddress: 0x%02X\n", + offset, i2c_index, i2c_address); + + chan = init_i2c_device_find(bios->dev, i2c_index); + if (!chan) + return -ENODEV; + + + ret = i2c_transfer(&chan->adapter, msg, 2); + if (ret < 0) { + BIOSLOG(bios, "0x%04X: I2CReg: 0x%02X:0x%02X, Value: [no device], " + "Mask: 0x%02X, Data: 0x%02X\n", + offset, reghi, reglo, mask, data); + iexec->execute = 0; + return 7; + } + + BIOSLOG(bios, "0x%04X: I2CReg: 0x%02X:0x%02X, Value: 0x%02X, " + "Mask: 0x%02X, Data: 0x%02X\n", + offset, reghi, reglo, buf1[0], mask, data); + + iexec->execute = ((buf1[0] & mask) == data); + + return 7; +} + +static struct init_tbl_entry itbl_entry[] = { + /* command name , id , length , offset , mult , command handler */ + /* INIT_PROG (0x31, 15, 10, 4) removed due to no example of use */ + { "INIT_IO_RESTRICT_PROG" , 0x32, init_io_restrict_prog }, + { "INIT_REPEAT" , 0x33, init_repeat }, + { "INIT_IO_RESTRICT_PLL" , 0x34, init_io_restrict_pll }, + { "INIT_END_REPEAT" , 0x36, init_end_repeat }, + { "INIT_COPY" , 0x37, init_copy }, + { "INIT_NOT" , 0x38, init_not }, + { "INIT_IO_FLAG_CONDITION" , 0x39, init_io_flag_condition }, + { "INIT_DP_CONDITION" , 0x3A, init_dp_condition }, + { "INIT_OP_3B" , 0x3B, init_op_3b }, + { "INIT_OP_3C" , 0x3C, init_op_3c }, + { "INIT_INDEX_ADDRESS_LATCHED" , 0x49, init_idx_addr_latched }, + { "INIT_IO_RESTRICT_PLL2" , 0x4A, init_io_restrict_pll2 }, + { "INIT_PLL2" , 0x4B, init_pll2 }, + { "INIT_I2C_BYTE" , 0x4C, init_i2c_byte }, + { "INIT_ZM_I2C_BYTE" , 0x4D, init_zm_i2c_byte }, + { "INIT_ZM_I2C" , 0x4E, init_zm_i2c }, + { "INIT_TMDS" , 0x4F, init_tmds }, + { "INIT_ZM_TMDS_GROUP" , 0x50, init_zm_tmds_group }, + { "INIT_CR_INDEX_ADDRESS_LATCHED" , 0x51, init_cr_idx_adr_latch }, + { "INIT_CR" , 0x52, init_cr }, + { "INIT_ZM_CR" , 0x53, init_zm_cr }, + { "INIT_ZM_CR_GROUP" , 0x54, init_zm_cr_group }, + { "INIT_CONDITION_TIME" , 0x56, init_condition_time }, + { "INIT_LTIME" , 0x57, init_ltime }, + { "INIT_ZM_REG_SEQUENCE" , 0x58, init_zm_reg_sequence }, + /* INIT_INDIRECT_REG (0x5A, 7, 0, 0) removed due to no example of use */ + { "INIT_SUB_DIRECT" , 0x5B, init_sub_direct }, + { "INIT_I2C_IF" , 0x5E, init_i2c_if }, + { "INIT_COPY_NV_REG" , 0x5F, init_copy_nv_reg }, + { "INIT_ZM_INDEX_IO" , 0x62, init_zm_index_io }, + { "INIT_COMPUTE_MEM" , 0x63, init_compute_mem }, + { "INIT_RESET" , 0x65, init_reset }, + { "INIT_CONFIGURE_MEM" , 0x66, init_configure_mem }, + { "INIT_CONFIGURE_CLK" , 0x67, init_configure_clk }, + { "INIT_CONFIGURE_PREINIT" , 0x68, init_configure_preinit }, + { "INIT_IO" , 0x69, init_io }, + { "INIT_SUB" , 0x6B, init_sub }, + { "INIT_RAM_CONDITION" , 0x6D, init_ram_condition }, + { "INIT_NV_REG" , 0x6E, init_nv_reg }, + { "INIT_MACRO" , 0x6F, init_macro }, + { "INIT_DONE" , 0x71, init_done }, + { "INIT_RESUME" , 0x72, init_resume }, + /* INIT_RAM_CONDITION2 (0x73, 9, 0, 0) removed due to no example of use */ + { "INIT_TIME" , 0x74, init_time }, + { "INIT_CONDITION" , 0x75, init_condition }, + { "INIT_IO_CONDITION" , 0x76, init_io_condition }, + { "INIT_INDEX_IO" , 0x78, init_index_io }, + { "INIT_PLL" , 0x79, init_pll }, + { "INIT_ZM_REG" , 0x7A, init_zm_reg }, + { "INIT_RAM_RESTRICT_PLL" , 0x87, init_ram_restrict_pll }, + { "INIT_8C" , 0x8C, init_8c }, + { "INIT_8D" , 0x8D, init_8d }, + { "INIT_GPIO" , 0x8E, init_gpio }, + { "INIT_RAM_RESTRICT_ZM_REG_GROUP" , 0x8F, init_ram_restrict_zm_reg_group }, + { "INIT_COPY_ZM_REG" , 0x90, init_copy_zm_reg }, + { "INIT_ZM_REG_GROUP_ADDRESS_LATCHED" , 0x91, init_zm_reg_group_addr_latched }, + { "INIT_RESERVED" , 0x92, init_reserved }, + { "INIT_96" , 0x96, init_96 }, + { "INIT_97" , 0x97, init_97 }, + { "INIT_AUXCH" , 0x98, init_auxch }, + { "INIT_ZM_AUXCH" , 0x99, init_zm_auxch }, + { "INIT_I2C_LONG_IF" , 0x9A, init_i2c_long_if }, + { NULL , 0 , NULL } +}; + +#define MAX_TABLE_OPS 1000 + +static int +parse_init_table(struct nvbios *bios, unsigned int offset, + struct init_exec *iexec) +{ + /* + * Parses all commands in an init table. + * + * We start out executing all commands found in the init table. Some + * opcodes may change the status of iexec->execute to SKIP, which will + * cause the following opcodes to perform no operation until the value + * is changed back to EXECUTE. + */ + + int count = 0, i, ret; + uint8_t id; + + /* + * Loop until INIT_DONE causes us to break out of the loop + * (or until offset > bios length just in case... ) + * (and no more than MAX_TABLE_OPS iterations, just in case... ) + */ + while ((offset < bios->length) && (count++ < MAX_TABLE_OPS)) { + id = bios->data[offset]; + + /* Find matching id in itbl_entry */ + for (i = 0; itbl_entry[i].name && (itbl_entry[i].id != id); i++) + ; + + if (!itbl_entry[i].name) { + NV_ERROR(bios->dev, + "0x%04X: Init table command not found: " + "0x%02X\n", offset, id); + return -ENOENT; + } + + BIOSLOG(bios, "0x%04X: [ (0x%02X) - %s ]\n", offset, + itbl_entry[i].id, itbl_entry[i].name); + + /* execute eventual command handler */ + ret = (*itbl_entry[i].handler)(bios, offset, iexec); + if (ret < 0) { + NV_ERROR(bios->dev, "0x%04X: Failed parsing init " + "table opcode: %s %d\n", offset, + itbl_entry[i].name, ret); + } + + if (ret <= 0) + break; + + /* + * Add the offset of the current command including all data + * of that command. The offset will then be pointing on the + * next op code. + */ + offset += ret; + } + + if (offset >= bios->length) + NV_WARN(bios->dev, + "Offset 0x%04X greater than known bios image length. " + "Corrupt image?\n", offset); + if (count >= MAX_TABLE_OPS) + NV_WARN(bios->dev, + "More than %d opcodes to a table is unlikely, " + "is the bios image corrupt?\n", MAX_TABLE_OPS); + + return 0; +} + +static void +parse_init_tables(struct nvbios *bios) +{ + /* Loops and calls parse_init_table() for each present table. */ + + int i = 0; + uint16_t table; + struct init_exec iexec = {true, false}; + + if (bios->old_style_init) { + if (bios->init_script_tbls_ptr) + parse_init_table(bios, bios->init_script_tbls_ptr, &iexec); + if (bios->extra_init_script_tbl_ptr) + parse_init_table(bios, bios->extra_init_script_tbl_ptr, &iexec); + + return; + } + + while ((table = ROM16(bios->data[bios->init_script_tbls_ptr + i]))) { + NV_INFO(bios->dev, + "Parsing VBIOS init table %d at offset 0x%04X\n", + i / 2, table); + BIOSLOG(bios, "0x%04X: ------ Executing following commands ------\n", table); + + parse_init_table(bios, table, &iexec); + i += 2; + } +} + +static uint16_t clkcmptable(struct nvbios *bios, uint16_t clktable, int pxclk) +{ + int compare_record_len, i = 0; + uint16_t compareclk, scriptptr = 0; + + if (bios->major_version < 5) /* pre BIT */ + compare_record_len = 3; + else + compare_record_len = 4; + + do { + compareclk = ROM16(bios->data[clktable + compare_record_len * i]); + if (pxclk >= compareclk * 10) { + if (bios->major_version < 5) { + uint8_t tmdssub = bios->data[clktable + 2 + compare_record_len * i]; + scriptptr = ROM16(bios->data[bios->init_script_tbls_ptr + tmdssub * 2]); + } else + scriptptr = ROM16(bios->data[clktable + 2 + compare_record_len * i]); + break; + } + i++; + } while (compareclk); + + return scriptptr; +} + +static void +run_digital_op_script(struct drm_device *dev, uint16_t scriptptr, + struct dcb_entry *dcbent, int head, bool dl) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + struct init_exec iexec = {true, false}; + + NV_TRACE(dev, "0x%04X: Parsing digital output script table\n", + scriptptr); + bios_idxprt_wr(bios, NV_CIO_CRX__COLOR, NV_CIO_CRE_44, + head ? NV_CIO_CRE_44_HEADB : NV_CIO_CRE_44_HEADA); + /* note: if dcb entries have been merged, index may be misleading */ + NVWriteVgaCrtc5758(dev, head, 0, dcbent->index); + parse_init_table(bios, scriptptr, &iexec); + + nv04_dfp_bind_head(dev, dcbent, head, dl); +} + +static int call_lvds_manufacturer_script(struct drm_device *dev, struct dcb_entry *dcbent, int head, enum LVDS_script script) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + uint8_t sub = bios->data[bios->fp.xlated_entry + script] + (bios->fp.link_c_increment && dcbent->or & OUTPUT_C ? 1 : 0); + uint16_t scriptofs = ROM16(bios->data[bios->init_script_tbls_ptr + sub * 2]); + + if (!bios->fp.xlated_entry || !sub || !scriptofs) + return -EINVAL; + + run_digital_op_script(dev, scriptofs, dcbent, head, bios->fp.dual_link); + + if (script == LVDS_PANEL_OFF) { + /* off-on delay in ms */ + msleep(ROM16(bios->data[bios->fp.xlated_entry + 7])); + } +#ifdef __powerpc__ + /* Powerbook specific quirks */ + if (script == LVDS_RESET && + (dev->pci_device == 0x0179 || dev->pci_device == 0x0189 || + dev->pci_device == 0x0329)) + nv_write_tmds(dev, dcbent->or, 0, 0x02, 0x72); +#endif + + return 0; +} + +static int run_lvds_table(struct drm_device *dev, struct dcb_entry *dcbent, int head, enum LVDS_script script, int pxclk) +{ + /* + * The BIT LVDS table's header has the information to setup the + * necessary registers. Following the standard 4 byte header are: + * A bitmask byte and a dual-link transition pxclk value for use in + * selecting the init script when not using straps; 4 script pointers + * for panel power, selected by output and on/off; and 8 table pointers + * for panel init, the needed one determined by output, and bits in the + * conf byte. These tables are similar to the TMDS tables, consisting + * of a list of pxclks and script pointers. + */ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + unsigned int outputset = (dcbent->or == 4) ? 1 : 0; + uint16_t scriptptr = 0, clktable; + + /* + * For now we assume version 3.0 table - g80 support will need some + * changes + */ + + switch (script) { + case LVDS_INIT: + return -ENOSYS; + case LVDS_BACKLIGHT_ON: + case LVDS_PANEL_ON: + scriptptr = ROM16(bios->data[bios->fp.lvdsmanufacturerpointer + 7 + outputset * 2]); + break; + case LVDS_BACKLIGHT_OFF: + case LVDS_PANEL_OFF: + scriptptr = ROM16(bios->data[bios->fp.lvdsmanufacturerpointer + 11 + outputset * 2]); + break; + case LVDS_RESET: + clktable = bios->fp.lvdsmanufacturerpointer + 15; + if (dcbent->or == 4) + clktable += 8; + + if (dcbent->lvdsconf.use_straps_for_mode) { + if (bios->fp.dual_link) + clktable += 4; + if (bios->fp.if_is_24bit) + clktable += 2; + } else { + /* using EDID */ + int cmpval_24bit = (dcbent->or == 4) ? 4 : 1; + + if (bios->fp.dual_link) { + clktable += 4; + cmpval_24bit <<= 1; + } + + if (bios->fp.strapless_is_24bit & cmpval_24bit) + clktable += 2; + } + + clktable = ROM16(bios->data[clktable]); + if (!clktable) { + NV_ERROR(dev, "Pixel clock comparison table not found\n"); + return -ENOENT; + } + scriptptr = clkcmptable(bios, clktable, pxclk); + } + + if (!scriptptr) { + NV_ERROR(dev, "LVDS output init script not found\n"); + return -ENOENT; + } + run_digital_op_script(dev, scriptptr, dcbent, head, bios->fp.dual_link); + + return 0; +} + +int call_lvds_script(struct drm_device *dev, struct dcb_entry *dcbent, int head, enum LVDS_script script, int pxclk) +{ + /* + * LVDS operations are multiplexed in an effort to present a single API + * which works with two vastly differing underlying structures. + * This acts as the demux + */ + + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + uint8_t lvds_ver = bios->data[bios->fp.lvdsmanufacturerpointer]; + uint32_t sel_clk_binding, sel_clk; + int ret; + + if (bios->fp.last_script_invoc == (script << 1 | head) || !lvds_ver || + (lvds_ver >= 0x30 && script == LVDS_INIT)) + return 0; + + if (!bios->fp.lvds_init_run) { + bios->fp.lvds_init_run = true; + call_lvds_script(dev, dcbent, head, LVDS_INIT, pxclk); + } + + if (script == LVDS_PANEL_ON && bios->fp.reset_after_pclk_change) + call_lvds_script(dev, dcbent, head, LVDS_RESET, pxclk); + if (script == LVDS_RESET && bios->fp.power_off_for_reset) + call_lvds_script(dev, dcbent, head, LVDS_PANEL_OFF, pxclk); + + NV_TRACE(dev, "Calling LVDS script %d:\n", script); + + /* don't let script change pll->head binding */ + sel_clk_binding = bios_rd32(bios, NV_PRAMDAC_SEL_CLK) & 0x50000; + + if (lvds_ver < 0x30) + ret = call_lvds_manufacturer_script(dev, dcbent, head, script); + else + ret = run_lvds_table(dev, dcbent, head, script, pxclk); + + bios->fp.last_script_invoc = (script << 1 | head); + + sel_clk = NVReadRAMDAC(dev, 0, NV_PRAMDAC_SEL_CLK) & ~0x50000; + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_SEL_CLK, sel_clk | sel_clk_binding); + /* some scripts set a value in NV_PBUS_POWERCTRL_2 and break video overlay */ + nvWriteMC(dev, NV_PBUS_POWERCTRL_2, 0); + + return ret; +} + +struct lvdstableheader { + uint8_t lvds_ver, headerlen, recordlen; +}; + +static int parse_lvds_manufacturer_table_header(struct drm_device *dev, struct nvbios *bios, struct lvdstableheader *lth) +{ + /* + * BMP version (0xa) LVDS table has a simple header of version and + * record length. The BIT LVDS table has the typical BIT table header: + * version byte, header length byte, record length byte, and a byte for + * the maximum number of records that can be held in the table. + */ + + uint8_t lvds_ver, headerlen, recordlen; + + memset(lth, 0, sizeof(struct lvdstableheader)); + + if (bios->fp.lvdsmanufacturerpointer == 0x0) { + NV_ERROR(dev, "Pointer to LVDS manufacturer table invalid\n"); + return -EINVAL; + } + + lvds_ver = bios->data[bios->fp.lvdsmanufacturerpointer]; + + switch (lvds_ver) { + case 0x0a: /* pre NV40 */ + headerlen = 2; + recordlen = bios->data[bios->fp.lvdsmanufacturerpointer + 1]; + break; + case 0x30: /* NV4x */ + headerlen = bios->data[bios->fp.lvdsmanufacturerpointer + 1]; + if (headerlen < 0x1f) { + NV_ERROR(dev, "LVDS table header not understood\n"); + return -EINVAL; + } + recordlen = bios->data[bios->fp.lvdsmanufacturerpointer + 2]; + break; + case 0x40: /* G80/G90 */ + headerlen = bios->data[bios->fp.lvdsmanufacturerpointer + 1]; + if (headerlen < 0x7) { + NV_ERROR(dev, "LVDS table header not understood\n"); + return -EINVAL; + } + recordlen = bios->data[bios->fp.lvdsmanufacturerpointer + 2]; + break; + default: + NV_ERROR(dev, + "LVDS table revision %d.%d not currently supported\n", + lvds_ver >> 4, lvds_ver & 0xf); + return -ENOSYS; + } + + lth->lvds_ver = lvds_ver; + lth->headerlen = headerlen; + lth->recordlen = recordlen; + + return 0; +} + +static int +get_fp_strap(struct drm_device *dev, struct nvbios *bios) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + /* + * The fp strap is normally dictated by the "User Strap" in + * PEXTDEV_BOOT_0[20:16], but on BMP cards when bit 2 of the + * Internal_Flags struct at 0x48 is set, the user strap gets overriden + * by the PCI subsystem ID during POST, but not before the previous user + * strap has been committed to CR58 for CR57=0xf on head A, which may be + * read and used instead + */ + + if (bios->major_version < 5 && bios->data[0x48] & 0x4) + return NVReadVgaCrtc5758(dev, 0, 0xf) & 0xf; + + if (dev_priv->card_type >= NV_50) + return (bios_rd32(bios, NV_PEXTDEV_BOOT_0) >> 24) & 0xf; + else + return (bios_rd32(bios, NV_PEXTDEV_BOOT_0) >> 16) & 0xf; +} + +static int parse_fp_mode_table(struct drm_device *dev, struct nvbios *bios) +{ + uint8_t *fptable; + uint8_t fptable_ver, headerlen = 0, recordlen, fpentries = 0xf, fpindex; + int ret, ofs, fpstrapping; + struct lvdstableheader lth; + + if (bios->fp.fptablepointer == 0x0) { + /* Apple cards don't have the fp table; the laptops use DDC */ + /* The table is also missing on some x86 IGPs */ +#ifndef __powerpc__ + NV_ERROR(dev, "Pointer to flat panel table invalid\n"); +#endif + bios->digital_min_front_porch = 0x4b; + return 0; + } + + fptable = &bios->data[bios->fp.fptablepointer]; + fptable_ver = fptable[0]; + + switch (fptable_ver) { + /* + * BMP version 0x5.0x11 BIOSen have version 1 like tables, but no + * version field, and miss one of the spread spectrum/PWM bytes. + * This could affect early GF2Go parts (not seen any appropriate ROMs + * though). Here we assume that a version of 0x05 matches this case + * (combining with a BMP version check would be better), as the + * common case for the panel type field is 0x0005, and that is in + * fact what we are reading the first byte of. + */ + case 0x05: /* some NV10, 11, 15, 16 */ + recordlen = 42; + ofs = -1; + break; + case 0x10: /* some NV15/16, and NV11+ */ + recordlen = 44; + ofs = 0; + break; + case 0x20: /* NV40+ */ + headerlen = fptable[1]; + recordlen = fptable[2]; + fpentries = fptable[3]; + /* + * fptable[4] is the minimum + * RAMDAC_FP_HCRTC -> RAMDAC_FP_HSYNC_START gap + */ + bios->digital_min_front_porch = fptable[4]; + ofs = -7; + break; + default: + NV_ERROR(dev, + "FP table revision %d.%d not currently supported\n", + fptable_ver >> 4, fptable_ver & 0xf); + return -ENOSYS; + } + + if (!bios->is_mobile) /* !mobile only needs digital_min_front_porch */ + return 0; + + ret = parse_lvds_manufacturer_table_header(dev, bios, <h); + if (ret) + return ret; + + if (lth.lvds_ver == 0x30 || lth.lvds_ver == 0x40) { + bios->fp.fpxlatetableptr = bios->fp.lvdsmanufacturerpointer + + lth.headerlen + 1; + bios->fp.xlatwidth = lth.recordlen; + } + if (bios->fp.fpxlatetableptr == 0x0) { + NV_ERROR(dev, "Pointer to flat panel xlat table invalid\n"); + return -EINVAL; + } + + fpstrapping = get_fp_strap(dev, bios); + + fpindex = bios->data[bios->fp.fpxlatetableptr + + fpstrapping * bios->fp.xlatwidth]; + + if (fpindex > fpentries) { + NV_ERROR(dev, "Bad flat panel table index\n"); + return -ENOENT; + } + + /* nv4x cards need both a strap value and fpindex of 0xf to use DDC */ + if (lth.lvds_ver > 0x10) + bios->fp_no_ddc = fpstrapping != 0xf || fpindex != 0xf; + + /* + * If either the strap or xlated fpindex value are 0xf there is no + * panel using a strap-derived bios mode present. this condition + * includes, but is different from, the DDC panel indicator above + */ + if (fpstrapping == 0xf || fpindex == 0xf) + return 0; + + bios->fp.mode_ptr = bios->fp.fptablepointer + headerlen + + recordlen * fpindex + ofs; + + NV_TRACE(dev, "BIOS FP mode: %dx%d (%dkHz pixel clock)\n", + ROM16(bios->data[bios->fp.mode_ptr + 11]) + 1, + ROM16(bios->data[bios->fp.mode_ptr + 25]) + 1, + ROM16(bios->data[bios->fp.mode_ptr + 7]) * 10); + + return 0; +} + +bool nouveau_bios_fp_mode(struct drm_device *dev, struct drm_display_mode *mode) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + uint8_t *mode_entry = &bios->data[bios->fp.mode_ptr]; + + if (!mode) /* just checking whether we can produce a mode */ + return bios->fp.mode_ptr; + + memset(mode, 0, sizeof(struct drm_display_mode)); + /* + * For version 1.0 (version in byte 0): + * bytes 1-2 are "panel type", including bits on whether Colour/mono, + * single/dual link, and type (TFT etc.) + * bytes 3-6 are bits per colour in RGBX + */ + mode->clock = ROM16(mode_entry[7]) * 10; + /* bytes 9-10 is HActive */ + mode->hdisplay = ROM16(mode_entry[11]) + 1; + /* + * bytes 13-14 is HValid Start + * bytes 15-16 is HValid End + */ + mode->hsync_start = ROM16(mode_entry[17]) + 1; + mode->hsync_end = ROM16(mode_entry[19]) + 1; + mode->htotal = ROM16(mode_entry[21]) + 1; + /* bytes 23-24, 27-30 similarly, but vertical */ + mode->vdisplay = ROM16(mode_entry[25]) + 1; + mode->vsync_start = ROM16(mode_entry[31]) + 1; + mode->vsync_end = ROM16(mode_entry[33]) + 1; + mode->vtotal = ROM16(mode_entry[35]) + 1; + mode->flags |= (mode_entry[37] & 0x10) ? + DRM_MODE_FLAG_PHSYNC : DRM_MODE_FLAG_NHSYNC; + mode->flags |= (mode_entry[37] & 0x1) ? + DRM_MODE_FLAG_PVSYNC : DRM_MODE_FLAG_NVSYNC; + /* + * bytes 38-39 relate to spread spectrum settings + * bytes 40-43 are something to do with PWM + */ + + mode->status = MODE_OK; + mode->type = DRM_MODE_TYPE_DRIVER | DRM_MODE_TYPE_PREFERRED; + drm_mode_set_name(mode); + return bios->fp.mode_ptr; +} + +int nouveau_bios_parse_lvds_table(struct drm_device *dev, int pxclk, bool *dl, bool *if_is_24bit) +{ + /* + * The LVDS table header is (mostly) described in + * parse_lvds_manufacturer_table_header(): the BIT header additionally + * contains the dual-link transition pxclk (in 10s kHz), at byte 5 - if + * straps are not being used for the panel, this specifies the frequency + * at which modes should be set up in the dual link style. + * + * Following the header, the BMP (ver 0xa) table has several records, + * indexed by a separate xlat table, indexed in turn by the fp strap in + * EXTDEV_BOOT. Each record had a config byte, followed by 6 script + * numbers for use by INIT_SUB which controlled panel init and power, + * and finally a dword of ms to sleep between power off and on + * operations. + * + * In the BIT versions, the table following the header serves as an + * integrated config and xlat table: the records in the table are + * indexed by the FP strap nibble in EXTDEV_BOOT, and each record has + * two bytes - the first as a config byte, the second for indexing the + * fp mode table pointed to by the BIT 'D' table + * + * DDC is not used until after card init, so selecting the correct table + * entry and setting the dual link flag for EDID equipped panels, + * requiring tests against the native-mode pixel clock, cannot be done + * until later, when this function should be called with non-zero pxclk + */ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + int fpstrapping = get_fp_strap(dev, bios), lvdsmanufacturerindex = 0; + struct lvdstableheader lth; + uint16_t lvdsofs; + int ret, chip_version = bios->chip_version; + + ret = parse_lvds_manufacturer_table_header(dev, bios, <h); + if (ret) + return ret; + + switch (lth.lvds_ver) { + case 0x0a: /* pre NV40 */ + lvdsmanufacturerindex = bios->data[ + bios->fp.fpxlatemanufacturertableptr + + fpstrapping]; + + /* we're done if this isn't the EDID panel case */ + if (!pxclk) + break; + + if (chip_version < 0x25) { + /* nv17 behaviour + * + * It seems the old style lvds script pointer is reused + * to select 18/24 bit colour depth for EDID panels. + */ + lvdsmanufacturerindex = + (bios->legacy.lvds_single_a_script_ptr & 1) ? + 2 : 0; + if (pxclk >= bios->fp.duallink_transition_clk) + lvdsmanufacturerindex++; + } else if (chip_version < 0x30) { + /* nv28 behaviour (off-chip encoder) + * + * nv28 does a complex dance of first using byte 121 of + * the EDID to choose the lvdsmanufacturerindex, then + * later attempting to match the EDID manufacturer and + * product IDs in a table (signature 'pidt' (panel id + * table?)), setting an lvdsmanufacturerindex of 0 and + * an fp strap of the match index (or 0xf if none) + */ + lvdsmanufacturerindex = 0; + } else { + /* nv31, nv34 behaviour */ + lvdsmanufacturerindex = 0; + if (pxclk >= bios->fp.duallink_transition_clk) + lvdsmanufacturerindex = 2; + if (pxclk >= 140000) + lvdsmanufacturerindex = 3; + } + + /* + * nvidia set the high nibble of (cr57=f, cr58) to + * lvdsmanufacturerindex in this case; we don't + */ + break; + case 0x30: /* NV4x */ + case 0x40: /* G80/G90 */ + lvdsmanufacturerindex = fpstrapping; + break; + default: + NV_ERROR(dev, "LVDS table revision not currently supported\n"); + return -ENOSYS; + } + + lvdsofs = bios->fp.xlated_entry = bios->fp.lvdsmanufacturerpointer + lth.headerlen + lth.recordlen * lvdsmanufacturerindex; + switch (lth.lvds_ver) { + case 0x0a: + bios->fp.power_off_for_reset = bios->data[lvdsofs] & 1; + bios->fp.reset_after_pclk_change = bios->data[lvdsofs] & 2; + bios->fp.dual_link = bios->data[lvdsofs] & 4; + bios->fp.link_c_increment = bios->data[lvdsofs] & 8; + *if_is_24bit = bios->data[lvdsofs] & 16; + break; + case 0x30: + case 0x40: + /* + * No sign of the "power off for reset" or "reset for panel + * on" bits, but it's safer to assume we should + */ + bios->fp.power_off_for_reset = true; + bios->fp.reset_after_pclk_change = true; + + /* + * It's ok lvdsofs is wrong for nv4x edid case; dual_link is + * over-written, and if_is_24bit isn't used + */ + bios->fp.dual_link = bios->data[lvdsofs] & 1; + bios->fp.if_is_24bit = bios->data[lvdsofs] & 2; + bios->fp.strapless_is_24bit = bios->data[bios->fp.lvdsmanufacturerpointer + 4]; + bios->fp.duallink_transition_clk = ROM16(bios->data[bios->fp.lvdsmanufacturerpointer + 5]) * 10; + break; + } + + /* Dell Latitude D620 reports a too-high value for the dual-link + * transition freq, causing us to program the panel incorrectly. + * + * It doesn't appear the VBIOS actually uses its transition freq + * (90000kHz), instead it uses the "Number of LVDS channels" field + * out of the panel ID structure (http://www.spwg.org/). + * + * For the moment, a quirk will do :) + */ + if (nv_match_device(dev, 0x01d7, 0x1028, 0x01c2)) + bios->fp.duallink_transition_clk = 80000; + + /* set dual_link flag for EDID case */ + if (pxclk && (chip_version < 0x25 || chip_version > 0x28)) + bios->fp.dual_link = (pxclk >= bios->fp.duallink_transition_clk); + + *dl = bios->fp.dual_link; + + return 0; +} + +static uint8_t * +bios_output_config_match(struct drm_device *dev, struct dcb_entry *dcbent, + uint16_t record, int record_len, int record_nr, + bool match_link) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + uint32_t entry; + uint16_t table; + int i, v; + + switch (dcbent->type) { + case OUTPUT_TMDS: + case OUTPUT_LVDS: + case OUTPUT_DP: + break; + default: + match_link = false; + break; + } + + for (i = 0; i < record_nr; i++, record += record_len) { + table = ROM16(bios->data[record]); + if (!table) + continue; + entry = ROM32(bios->data[table]); + + if (match_link) { + v = (entry & 0x00c00000) >> 22; + if (!(v & dcbent->sorconf.link)) + continue; + } + + v = (entry & 0x000f0000) >> 16; + if (!(v & dcbent->or)) + continue; + + v = (entry & 0x000000f0) >> 4; + if (v != dcbent->location) + continue; + + v = (entry & 0x0000000f); + if (v != dcbent->type) + continue; + + return &bios->data[table]; + } + + return NULL; +} + +void * +nouveau_bios_dp_table(struct drm_device *dev, struct dcb_entry *dcbent, + int *length) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + uint8_t *table; + + if (!bios->display.dp_table_ptr) { + NV_ERROR(dev, "No pointer to DisplayPort table\n"); + return NULL; + } + table = &bios->data[bios->display.dp_table_ptr]; + + if (table[0] != 0x20 && table[0] != 0x21) { + NV_ERROR(dev, "DisplayPort table version 0x%02x unknown\n", + table[0]); + return NULL; + } + + *length = table[4]; + return bios_output_config_match(dev, dcbent, + bios->display.dp_table_ptr + table[1], + table[2], table[3], table[0] >= 0x21); +} + +int +nouveau_bios_run_display_table(struct drm_device *dev, struct dcb_entry *dcbent, + uint32_t sub, int pxclk) +{ + /* + * The display script table is located by the BIT 'U' table. + * + * It contains an array of pointers to various tables describing + * a particular output type. The first 32-bits of the output + * tables contains similar information to a DCB entry, and is + * used to decide whether that particular table is suitable for + * the output you want to access. + * + * The "record header length" field here seems to indicate the + * offset of the first configuration entry in the output tables. + * This is 10 on most cards I've seen, but 12 has been witnessed + * on DP cards, and there's another script pointer within the + * header. + * + * offset + 0 ( 8 bits): version + * offset + 1 ( 8 bits): header length + * offset + 2 ( 8 bits): record length + * offset + 3 ( 8 bits): number of records + * offset + 4 ( 8 bits): record header length + * offset + 5 (16 bits): pointer to first output script table + */ + + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + uint8_t *table = &bios->data[bios->display.script_table_ptr]; + uint8_t *otable = NULL; + uint16_t script; + int i = 0; + + if (!bios->display.script_table_ptr) { + NV_ERROR(dev, "No pointer to output script table\n"); + return 1; + } + + /* + * Nothing useful has been in any of the pre-2.0 tables I've seen, + * so until they are, we really don't need to care. + */ + if (table[0] < 0x20) + return 1; + + if (table[0] != 0x20 && table[0] != 0x21) { + NV_ERROR(dev, "Output script table version 0x%02x unknown\n", + table[0]); + return 1; + } + + /* + * The output script tables describing a particular output type + * look as follows: + * + * offset + 0 (32 bits): output this table matches (hash of DCB) + * offset + 4 ( 8 bits): unknown + * offset + 5 ( 8 bits): number of configurations + * offset + 6 (16 bits): pointer to some script + * offset + 8 (16 bits): pointer to some script + * + * headerlen == 10 + * offset + 10 : configuration 0 + * + * headerlen == 12 + * offset + 10 : pointer to some script + * offset + 12 : configuration 0 + * + * Each config entry is as follows: + * + * offset + 0 (16 bits): unknown, assumed to be a match value + * offset + 2 (16 bits): pointer to script table (clock set?) + * offset + 4 (16 bits): pointer to script table (reset?) + * + * There doesn't appear to be a count value to say how many + * entries exist in each script table, instead, a 0 value in + * the first 16-bit word seems to indicate both the end of the + * list and the default entry. The second 16-bit word in the + * script tables is a pointer to the script to execute. + */ + + NV_DEBUG_KMS(dev, "Searching for output entry for %d %d %d\n", + dcbent->type, dcbent->location, dcbent->or); + otable = bios_output_config_match(dev, dcbent, table[1] + + bios->display.script_table_ptr, + table[2], table[3], table[0] >= 0x21); + if (!otable) { + NV_DEBUG_KMS(dev, "failed to match any output table\n"); + return 1; + } + + if (pxclk < -2 || pxclk > 0) { + /* Try to find matching script table entry */ + for (i = 0; i < otable[5]; i++) { + if (ROM16(otable[table[4] + i*6]) == sub) + break; + } + + if (i == otable[5]) { + NV_ERROR(dev, "Table 0x%04x not found for %d/%d, " + "using first\n", + sub, dcbent->type, dcbent->or); + i = 0; + } + } + + if (pxclk == 0) { + script = ROM16(otable[6]); + if (!script) { + NV_DEBUG_KMS(dev, "output script 0 not found\n"); + return 1; + } + + NV_DEBUG_KMS(dev, "0x%04X: parsing output script 0\n", script); + nouveau_bios_run_init_table(dev, script, dcbent); + } else + if (pxclk == -1) { + script = ROM16(otable[8]); + if (!script) { + NV_DEBUG_KMS(dev, "output script 1 not found\n"); + return 1; + } + + NV_DEBUG_KMS(dev, "0x%04X: parsing output script 1\n", script); + nouveau_bios_run_init_table(dev, script, dcbent); + } else + if (pxclk == -2) { + if (table[4] >= 12) + script = ROM16(otable[10]); + else + script = 0; + if (!script) { + NV_DEBUG_KMS(dev, "output script 2 not found\n"); + return 1; + } + + NV_DEBUG_KMS(dev, "0x%04X: parsing output script 2\n", script); + nouveau_bios_run_init_table(dev, script, dcbent); + } else + if (pxclk > 0) { + script = ROM16(otable[table[4] + i*6 + 2]); + if (script) + script = clkcmptable(bios, script, pxclk); + if (!script) { + NV_DEBUG_KMS(dev, "clock script 0 not found\n"); + return 1; + } + + NV_DEBUG_KMS(dev, "0x%04X: parsing clock script 0\n", script); + nouveau_bios_run_init_table(dev, script, dcbent); + } else + if (pxclk < 0) { + script = ROM16(otable[table[4] + i*6 + 4]); + if (script) + script = clkcmptable(bios, script, -pxclk); + if (!script) { + NV_DEBUG_KMS(dev, "clock script 1 not found\n"); + return 1; + } + + NV_DEBUG_KMS(dev, "0x%04X: parsing clock script 1\n", script); + nouveau_bios_run_init_table(dev, script, dcbent); + } + + return 0; +} + + +int run_tmds_table(struct drm_device *dev, struct dcb_entry *dcbent, int head, int pxclk) +{ + /* + * the pxclk parameter is in kHz + * + * This runs the TMDS regs setting code found on BIT bios cards + * + * For ffs(or) == 1 use the first table, for ffs(or) == 2 and + * ffs(or) == 3, use the second. + */ + + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + int cv = bios->chip_version; + uint16_t clktable = 0, scriptptr; + uint32_t sel_clk_binding, sel_clk; + + /* pre-nv17 off-chip tmds uses scripts, post nv17 doesn't */ + if (cv >= 0x17 && cv != 0x1a && cv != 0x20 && + dcbent->location != DCB_LOC_ON_CHIP) + return 0; + + switch (ffs(dcbent->or)) { + case 1: + clktable = bios->tmds.output0_script_ptr; + break; + case 2: + case 3: + clktable = bios->tmds.output1_script_ptr; + break; + } + + if (!clktable) { + NV_ERROR(dev, "Pixel clock comparison table not found\n"); + return -EINVAL; + } + + scriptptr = clkcmptable(bios, clktable, pxclk); + + if (!scriptptr) { + NV_ERROR(dev, "TMDS output init script not found\n"); + return -ENOENT; + } + + /* don't let script change pll->head binding */ + sel_clk_binding = bios_rd32(bios, NV_PRAMDAC_SEL_CLK) & 0x50000; + run_digital_op_script(dev, scriptptr, dcbent, head, pxclk >= 165000); + sel_clk = NVReadRAMDAC(dev, 0, NV_PRAMDAC_SEL_CLK) & ~0x50000; + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_SEL_CLK, sel_clk | sel_clk_binding); + + return 0; +} + +struct pll_mapping { + u8 type; + u32 reg; +}; + +static struct pll_mapping nv04_pll_mapping[] = { + { PLL_CORE , NV_PRAMDAC_NVPLL_COEFF }, + { PLL_MEMORY, NV_PRAMDAC_MPLL_COEFF }, + { PLL_VPLL0 , NV_PRAMDAC_VPLL_COEFF }, + { PLL_VPLL1 , NV_RAMDAC_VPLL2 }, + {} +}; + +static struct pll_mapping nv40_pll_mapping[] = { + { PLL_CORE , 0x004000 }, + { PLL_MEMORY, 0x004020 }, + { PLL_VPLL0 , NV_PRAMDAC_VPLL_COEFF }, + { PLL_VPLL1 , NV_RAMDAC_VPLL2 }, + {} +}; + +static struct pll_mapping nv50_pll_mapping[] = { + { PLL_CORE , 0x004028 }, + { PLL_SHADER, 0x004020 }, + { PLL_UNK03 , 0x004000 }, + { PLL_MEMORY, 0x004008 }, + { PLL_UNK40 , 0x00e810 }, + { PLL_UNK41 , 0x00e818 }, + { PLL_UNK42 , 0x00e824 }, + { PLL_VPLL0 , 0x614100 }, + { PLL_VPLL1 , 0x614900 }, + {} +}; + +static struct pll_mapping nv84_pll_mapping[] = { + { PLL_CORE , 0x004028 }, + { PLL_SHADER, 0x004020 }, + { PLL_MEMORY, 0x004008 }, + { PLL_UNK05 , 0x004030 }, + { PLL_UNK41 , 0x00e818 }, + { PLL_VPLL0 , 0x614100 }, + { PLL_VPLL1 , 0x614900 }, + {} +}; + +u32 +get_pll_register(struct drm_device *dev, enum pll_types type) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + struct pll_mapping *map; + int i; + + if (dev_priv->card_type < NV_40) + map = nv04_pll_mapping; + else + if (dev_priv->card_type < NV_50) + map = nv40_pll_mapping; + else { + u8 *plim = &bios->data[bios->pll_limit_tbl_ptr]; + + if (plim[0] >= 0x30) { + u8 *entry = plim + plim[1]; + for (i = 0; i < plim[3]; i++, entry += plim[2]) { + if (entry[0] == type) + return ROM32(entry[3]); + } + + return 0; + } + + if (dev_priv->chipset == 0x50) + map = nv50_pll_mapping; + else + map = nv84_pll_mapping; + } + + while (map->reg) { + if (map->type == type) + return map->reg; + map++; + } + + return 0; +} + +int get_pll_limits(struct drm_device *dev, uint32_t limit_match, struct pll_lims *pll_lim) +{ + /* + * PLL limits table + * + * Version 0x10: NV30, NV31 + * One byte header (version), one record of 24 bytes + * Version 0x11: NV36 - Not implemented + * Seems to have same record style as 0x10, but 3 records rather than 1 + * Version 0x20: Found on Geforce 6 cards + * Trivial 4 byte BIT header. 31 (0x1f) byte record length + * Version 0x21: Found on Geforce 7, 8 and some Geforce 6 cards + * 5 byte header, fifth byte of unknown purpose. 35 (0x23) byte record + * length in general, some (integrated) have an extra configuration byte + * Version 0x30: Found on Geforce 8, separates the register mapping + * from the limits tables. + */ + + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + int cv = bios->chip_version, pllindex = 0; + uint8_t pll_lim_ver = 0, headerlen = 0, recordlen = 0, entries = 0; + uint32_t crystal_strap_mask, crystal_straps; + + if (!bios->pll_limit_tbl_ptr) { + if (cv == 0x30 || cv == 0x31 || cv == 0x35 || cv == 0x36 || + cv >= 0x40) { + NV_ERROR(dev, "Pointer to PLL limits table invalid\n"); + return -EINVAL; + } + } else + pll_lim_ver = bios->data[bios->pll_limit_tbl_ptr]; + + crystal_strap_mask = 1 << 6; + /* open coded dev->twoHeads test */ + if (cv > 0x10 && cv != 0x15 && cv != 0x1a && cv != 0x20) + crystal_strap_mask |= 1 << 22; + crystal_straps = nvReadEXTDEV(dev, NV_PEXTDEV_BOOT_0) & + crystal_strap_mask; + + switch (pll_lim_ver) { + /* + * We use version 0 to indicate a pre limit table bios (single stage + * pll) and load the hard coded limits instead. + */ + case 0: + break; + case 0x10: + case 0x11: + /* + * Strictly v0x11 has 3 entries, but the last two don't seem + * to get used. + */ + headerlen = 1; + recordlen = 0x18; + entries = 1; + pllindex = 0; + break; + case 0x20: + case 0x21: + case 0x30: + case 0x40: + headerlen = bios->data[bios->pll_limit_tbl_ptr + 1]; + recordlen = bios->data[bios->pll_limit_tbl_ptr + 2]; + entries = bios->data[bios->pll_limit_tbl_ptr + 3]; + break; + default: + NV_ERROR(dev, "PLL limits table revision 0x%X not currently " + "supported\n", pll_lim_ver); + return -ENOSYS; + } + + /* initialize all members to zero */ + memset(pll_lim, 0, sizeof(struct pll_lims)); + + /* if we were passed a type rather than a register, figure + * out the register and store it + */ + if (limit_match > PLL_MAX) + pll_lim->reg = limit_match; + else { + pll_lim->reg = get_pll_register(dev, limit_match); + if (!pll_lim->reg) + return -ENOENT; + } + + if (pll_lim_ver == 0x10 || pll_lim_ver == 0x11) { + uint8_t *pll_rec = &bios->data[bios->pll_limit_tbl_ptr + headerlen + recordlen * pllindex]; + + pll_lim->vco1.minfreq = ROM32(pll_rec[0]); + pll_lim->vco1.maxfreq = ROM32(pll_rec[4]); + pll_lim->vco2.minfreq = ROM32(pll_rec[8]); + pll_lim->vco2.maxfreq = ROM32(pll_rec[12]); + pll_lim->vco1.min_inputfreq = ROM32(pll_rec[16]); + pll_lim->vco2.min_inputfreq = ROM32(pll_rec[20]); + pll_lim->vco1.max_inputfreq = pll_lim->vco2.max_inputfreq = INT_MAX; + + /* these values taken from nv30/31/36 */ + pll_lim->vco1.min_n = 0x1; + if (cv == 0x36) + pll_lim->vco1.min_n = 0x5; + pll_lim->vco1.max_n = 0xff; + pll_lim->vco1.min_m = 0x1; + pll_lim->vco1.max_m = 0xd; + pll_lim->vco2.min_n = 0x4; + /* + * On nv30, 31, 36 (i.e. all cards with two stage PLLs with this + * table version (apart from nv35)), N2 is compared to + * maxN2 (0x46) and 10 * maxM2 (0x4), so set maxN2 to 0x28 and + * save a comparison + */ + pll_lim->vco2.max_n = 0x28; + if (cv == 0x30 || cv == 0x35) + /* only 5 bits available for N2 on nv30/35 */ + pll_lim->vco2.max_n = 0x1f; + pll_lim->vco2.min_m = 0x1; + pll_lim->vco2.max_m = 0x4; + pll_lim->max_log2p = 0x7; + pll_lim->max_usable_log2p = 0x6; + } else if (pll_lim_ver == 0x20 || pll_lim_ver == 0x21) { + uint16_t plloffs = bios->pll_limit_tbl_ptr + headerlen; + uint8_t *pll_rec; + int i; + + /* + * First entry is default match, if nothing better. warn if + * reg field nonzero + */ + if (ROM32(bios->data[plloffs])) + NV_WARN(dev, "Default PLL limit entry has non-zero " + "register field\n"); + + for (i = 1; i < entries; i++) + if (ROM32(bios->data[plloffs + recordlen * i]) == pll_lim->reg) { + pllindex = i; + break; + } + + if ((dev_priv->card_type >= NV_50) && (pllindex == 0)) { + NV_ERROR(dev, "Register 0x%08x not found in PLL " + "limits table", pll_lim->reg); + return -ENOENT; + } + + pll_rec = &bios->data[plloffs + recordlen * pllindex]; + + BIOSLOG(bios, "Loading PLL limits for reg 0x%08x\n", + pllindex ? pll_lim->reg : 0); + + /* + * Frequencies are stored in tables in MHz, kHz are more + * useful, so we convert. + */ + + /* What output frequencies can each VCO generate? */ + pll_lim->vco1.minfreq = ROM16(pll_rec[4]) * 1000; + pll_lim->vco1.maxfreq = ROM16(pll_rec[6]) * 1000; + pll_lim->vco2.minfreq = ROM16(pll_rec[8]) * 1000; + pll_lim->vco2.maxfreq = ROM16(pll_rec[10]) * 1000; + + /* What input frequencies they accept (past the m-divider)? */ + pll_lim->vco1.min_inputfreq = ROM16(pll_rec[12]) * 1000; + pll_lim->vco2.min_inputfreq = ROM16(pll_rec[14]) * 1000; + pll_lim->vco1.max_inputfreq = ROM16(pll_rec[16]) * 1000; + pll_lim->vco2.max_inputfreq = ROM16(pll_rec[18]) * 1000; + + /* What values are accepted as multiplier and divider? */ + pll_lim->vco1.min_n = pll_rec[20]; + pll_lim->vco1.max_n = pll_rec[21]; + pll_lim->vco1.min_m = pll_rec[22]; + pll_lim->vco1.max_m = pll_rec[23]; + pll_lim->vco2.min_n = pll_rec[24]; + pll_lim->vco2.max_n = pll_rec[25]; + pll_lim->vco2.min_m = pll_rec[26]; + pll_lim->vco2.max_m = pll_rec[27]; + + pll_lim->max_usable_log2p = pll_lim->max_log2p = pll_rec[29]; + if (pll_lim->max_log2p > 0x7) + /* pll decoding in nv_hw.c assumes never > 7 */ + NV_WARN(dev, "Max log2 P value greater than 7 (%d)\n", + pll_lim->max_log2p); + if (cv < 0x60) + pll_lim->max_usable_log2p = 0x6; + pll_lim->log2p_bias = pll_rec[30]; + + if (recordlen > 0x22) + pll_lim->refclk = ROM32(pll_rec[31]); + + if (recordlen > 0x23 && pll_rec[35]) + NV_WARN(dev, + "Bits set in PLL configuration byte (%x)\n", + pll_rec[35]); + + /* C51 special not seen elsewhere */ + if (cv == 0x51 && !pll_lim->refclk) { + uint32_t sel_clk = bios_rd32(bios, NV_PRAMDAC_SEL_CLK); + + if ((pll_lim->reg == NV_PRAMDAC_VPLL_COEFF && sel_clk & 0x20) || + (pll_lim->reg == NV_RAMDAC_VPLL2 && sel_clk & 0x80)) { + if (bios_idxprt_rd(bios, NV_CIO_CRX__COLOR, NV_CIO_CRE_CHIP_ID_INDEX) < 0xa3) + pll_lim->refclk = 200000; + else + pll_lim->refclk = 25000; + } + } + } else if (pll_lim_ver == 0x30) { /* ver 0x30 */ + uint8_t *entry = &bios->data[bios->pll_limit_tbl_ptr + headerlen]; + uint8_t *record = NULL; + int i; + + BIOSLOG(bios, "Loading PLL limits for register 0x%08x\n", + pll_lim->reg); + + for (i = 0; i < entries; i++, entry += recordlen) { + if (ROM32(entry[3]) == pll_lim->reg) { + record = &bios->data[ROM16(entry[1])]; + break; + } + } + + if (!record) { + NV_ERROR(dev, "Register 0x%08x not found in PLL " + "limits table", pll_lim->reg); + return -ENOENT; + } + + pll_lim->vco1.minfreq = ROM16(record[0]) * 1000; + pll_lim->vco1.maxfreq = ROM16(record[2]) * 1000; + pll_lim->vco2.minfreq = ROM16(record[4]) * 1000; + pll_lim->vco2.maxfreq = ROM16(record[6]) * 1000; + pll_lim->vco1.min_inputfreq = ROM16(record[8]) * 1000; + pll_lim->vco2.min_inputfreq = ROM16(record[10]) * 1000; + pll_lim->vco1.max_inputfreq = ROM16(record[12]) * 1000; + pll_lim->vco2.max_inputfreq = ROM16(record[14]) * 1000; + pll_lim->vco1.min_n = record[16]; + pll_lim->vco1.max_n = record[17]; + pll_lim->vco1.min_m = record[18]; + pll_lim->vco1.max_m = record[19]; + pll_lim->vco2.min_n = record[20]; + pll_lim->vco2.max_n = record[21]; + pll_lim->vco2.min_m = record[22]; + pll_lim->vco2.max_m = record[23]; + pll_lim->max_usable_log2p = pll_lim->max_log2p = record[25]; + pll_lim->log2p_bias = record[27]; + pll_lim->refclk = ROM32(record[28]); + } else if (pll_lim_ver) { /* ver 0x40 */ + uint8_t *entry = &bios->data[bios->pll_limit_tbl_ptr + headerlen]; + uint8_t *record = NULL; + int i; + + BIOSLOG(bios, "Loading PLL limits for register 0x%08x\n", + pll_lim->reg); + + for (i = 0; i < entries; i++, entry += recordlen) { + if (ROM32(entry[3]) == pll_lim->reg) { + record = &bios->data[ROM16(entry[1])]; + break; + } + } + + if (!record) { + NV_ERROR(dev, "Register 0x%08x not found in PLL " + "limits table", pll_lim->reg); + return -ENOENT; + } + + pll_lim->vco1.minfreq = ROM16(record[0]) * 1000; + pll_lim->vco1.maxfreq = ROM16(record[2]) * 1000; + pll_lim->vco1.min_inputfreq = ROM16(record[4]) * 1000; + pll_lim->vco1.max_inputfreq = ROM16(record[6]) * 1000; + pll_lim->vco1.min_m = record[8]; + pll_lim->vco1.max_m = record[9]; + pll_lim->vco1.min_n = record[10]; + pll_lim->vco1.max_n = record[11]; + pll_lim->min_p = record[12]; + pll_lim->max_p = record[13]; + /* where did this go to?? */ + if ((entry[0] & 0xf0) == 0x80) + pll_lim->refclk = 27000; + else + pll_lim->refclk = 100000; + } + + /* + * By now any valid limit table ought to have set a max frequency for + * vco1, so if it's zero it's either a pre limit table bios, or one + * with an empty limit table (seen on nv18) + */ + if (!pll_lim->vco1.maxfreq) { + pll_lim->vco1.minfreq = bios->fminvco; + pll_lim->vco1.maxfreq = bios->fmaxvco; + pll_lim->vco1.min_inputfreq = 0; + pll_lim->vco1.max_inputfreq = INT_MAX; + pll_lim->vco1.min_n = 0x1; + pll_lim->vco1.max_n = 0xff; + pll_lim->vco1.min_m = 0x1; + if (crystal_straps == 0) { + /* nv05 does this, nv11 doesn't, nv10 unknown */ + if (cv < 0x11) + pll_lim->vco1.min_m = 0x7; + pll_lim->vco1.max_m = 0xd; + } else { + if (cv < 0x11) + pll_lim->vco1.min_m = 0x8; + pll_lim->vco1.max_m = 0xe; + } + if (cv < 0x17 || cv == 0x1a || cv == 0x20) + pll_lim->max_log2p = 4; + else + pll_lim->max_log2p = 5; + pll_lim->max_usable_log2p = pll_lim->max_log2p; + } + + if (!pll_lim->refclk) + switch (crystal_straps) { + case 0: + pll_lim->refclk = 13500; + break; + case (1 << 6): + pll_lim->refclk = 14318; + break; + case (1 << 22): + pll_lim->refclk = 27000; + break; + case (1 << 22 | 1 << 6): + pll_lim->refclk = 25000; + break; + } + + NV_DEBUG(dev, "pll.vco1.minfreq: %d\n", pll_lim->vco1.minfreq); + NV_DEBUG(dev, "pll.vco1.maxfreq: %d\n", pll_lim->vco1.maxfreq); + NV_DEBUG(dev, "pll.vco1.min_inputfreq: %d\n", pll_lim->vco1.min_inputfreq); + NV_DEBUG(dev, "pll.vco1.max_inputfreq: %d\n", pll_lim->vco1.max_inputfreq); + NV_DEBUG(dev, "pll.vco1.min_n: %d\n", pll_lim->vco1.min_n); + NV_DEBUG(dev, "pll.vco1.max_n: %d\n", pll_lim->vco1.max_n); + NV_DEBUG(dev, "pll.vco1.min_m: %d\n", pll_lim->vco1.min_m); + NV_DEBUG(dev, "pll.vco1.max_m: %d\n", pll_lim->vco1.max_m); + if (pll_lim->vco2.maxfreq) { + NV_DEBUG(dev, "pll.vco2.minfreq: %d\n", pll_lim->vco2.minfreq); + NV_DEBUG(dev, "pll.vco2.maxfreq: %d\n", pll_lim->vco2.maxfreq); + NV_DEBUG(dev, "pll.vco2.min_inputfreq: %d\n", pll_lim->vco2.min_inputfreq); + NV_DEBUG(dev, "pll.vco2.max_inputfreq: %d\n", pll_lim->vco2.max_inputfreq); + NV_DEBUG(dev, "pll.vco2.min_n: %d\n", pll_lim->vco2.min_n); + NV_DEBUG(dev, "pll.vco2.max_n: %d\n", pll_lim->vco2.max_n); + NV_DEBUG(dev, "pll.vco2.min_m: %d\n", pll_lim->vco2.min_m); + NV_DEBUG(dev, "pll.vco2.max_m: %d\n", pll_lim->vco2.max_m); + } + if (!pll_lim->max_p) { + NV_DEBUG(dev, "pll.max_log2p: %d\n", pll_lim->max_log2p); + NV_DEBUG(dev, "pll.log2p_bias: %d\n", pll_lim->log2p_bias); + } else { + NV_DEBUG(dev, "pll.min_p: %d\n", pll_lim->min_p); + NV_DEBUG(dev, "pll.max_p: %d\n", pll_lim->max_p); + } + NV_DEBUG(dev, "pll.refclk: %d\n", pll_lim->refclk); + + return 0; +} + +static void parse_bios_version(struct drm_device *dev, struct nvbios *bios, uint16_t offset) +{ + /* + * offset + 0 (8 bits): Micro version + * offset + 1 (8 bits): Minor version + * offset + 2 (8 bits): Chip version + * offset + 3 (8 bits): Major version + */ + + bios->major_version = bios->data[offset + 3]; + bios->chip_version = bios->data[offset + 2]; + NV_TRACE(dev, "Bios version %02x.%02x.%02x.%02x\n", + bios->data[offset + 3], bios->data[offset + 2], + bios->data[offset + 1], bios->data[offset]); +} + +static void parse_script_table_pointers(struct nvbios *bios, uint16_t offset) +{ + /* + * Parses the init table segment for pointers used in script execution. + * + * offset + 0 (16 bits): init script tables pointer + * offset + 2 (16 bits): macro index table pointer + * offset + 4 (16 bits): macro table pointer + * offset + 6 (16 bits): condition table pointer + * offset + 8 (16 bits): io condition table pointer + * offset + 10 (16 bits): io flag condition table pointer + * offset + 12 (16 bits): init function table pointer + */ + + bios->init_script_tbls_ptr = ROM16(bios->data[offset]); + bios->macro_index_tbl_ptr = ROM16(bios->data[offset + 2]); + bios->macro_tbl_ptr = ROM16(bios->data[offset + 4]); + bios->condition_tbl_ptr = ROM16(bios->data[offset + 6]); + bios->io_condition_tbl_ptr = ROM16(bios->data[offset + 8]); + bios->io_flag_condition_tbl_ptr = ROM16(bios->data[offset + 10]); + bios->init_function_tbl_ptr = ROM16(bios->data[offset + 12]); +} + +static int parse_bit_A_tbl_entry(struct drm_device *dev, struct nvbios *bios, struct bit_entry *bitentry) +{ + /* + * Parses the load detect values for g80 cards. + * + * offset + 0 (16 bits): loadval table pointer + */ + + uint16_t load_table_ptr; + uint8_t version, headerlen, entrylen, num_entries; + + if (bitentry->length != 3) { + NV_ERROR(dev, "Do not understand BIT A table\n"); + return -EINVAL; + } + + load_table_ptr = ROM16(bios->data[bitentry->offset]); + + if (load_table_ptr == 0x0) { + NV_ERROR(dev, "Pointer to BIT loadval table invalid\n"); + return -EINVAL; + } + + version = bios->data[load_table_ptr]; + + if (version != 0x10) { + NV_ERROR(dev, "BIT loadval table version %d.%d not supported\n", + version >> 4, version & 0xF); + return -ENOSYS; + } + + headerlen = bios->data[load_table_ptr + 1]; + entrylen = bios->data[load_table_ptr + 2]; + num_entries = bios->data[load_table_ptr + 3]; + + if (headerlen != 4 || entrylen != 4 || num_entries != 2) { + NV_ERROR(dev, "Do not understand BIT loadval table\n"); + return -EINVAL; + } + + /* First entry is normal dac, 2nd tv-out perhaps? */ + bios->dactestval = ROM32(bios->data[load_table_ptr + headerlen]) & 0x3ff; + + return 0; +} + +static int parse_bit_C_tbl_entry(struct drm_device *dev, struct nvbios *bios, struct bit_entry *bitentry) +{ + /* + * offset + 8 (16 bits): PLL limits table pointer + * + * There's more in here, but that's unknown. + */ + + if (bitentry->length < 10) { + NV_ERROR(dev, "Do not understand BIT C table\n"); + return -EINVAL; + } + + bios->pll_limit_tbl_ptr = ROM16(bios->data[bitentry->offset + 8]); + + return 0; +} + +static int parse_bit_display_tbl_entry(struct drm_device *dev, struct nvbios *bios, struct bit_entry *bitentry) +{ + /* + * Parses the flat panel table segment that the bit entry points to. + * Starting at bitentry->offset: + * + * offset + 0 (16 bits): ??? table pointer - seems to have 18 byte + * records beginning with a freq. + * offset + 2 (16 bits): mode table pointer + */ + + if (bitentry->length != 4) { + NV_ERROR(dev, "Do not understand BIT display table\n"); + return -EINVAL; + } + + bios->fp.fptablepointer = ROM16(bios->data[bitentry->offset + 2]); + + return 0; +} + +static int parse_bit_init_tbl_entry(struct drm_device *dev, struct nvbios *bios, struct bit_entry *bitentry) +{ + /* + * Parses the init table segment that the bit entry points to. + * + * See parse_script_table_pointers for layout + */ + + if (bitentry->length < 14) { + NV_ERROR(dev, "Do not understand init table\n"); + return -EINVAL; + } + + parse_script_table_pointers(bios, bitentry->offset); + + if (bitentry->length >= 16) + bios->some_script_ptr = ROM16(bios->data[bitentry->offset + 14]); + if (bitentry->length >= 18) + bios->init96_tbl_ptr = ROM16(bios->data[bitentry->offset + 16]); + + return 0; +} + +static int parse_bit_i_tbl_entry(struct drm_device *dev, struct nvbios *bios, struct bit_entry *bitentry) +{ + /* + * BIT 'i' (info?) table + * + * offset + 0 (32 bits): BIOS version dword (as in B table) + * offset + 5 (8 bits): BIOS feature byte (same as for BMP?) + * offset + 13 (16 bits): pointer to table containing DAC load + * detection comparison values + * + * There's other things in the table, purpose unknown + */ + + uint16_t daccmpoffset; + uint8_t dacver, dacheaderlen; + + if (bitentry->length < 6) { + NV_ERROR(dev, "BIT i table too short for needed information\n"); + return -EINVAL; + } + + parse_bios_version(dev, bios, bitentry->offset); + + /* + * bit 4 seems to indicate a mobile bios (doesn't suffer from BMP's + * Quadro identity crisis), other bits possibly as for BMP feature byte + */ + bios->feature_byte = bios->data[bitentry->offset + 5]; + bios->is_mobile = bios->feature_byte & FEATURE_MOBILE; + + if (bitentry->length < 15) { + NV_WARN(dev, "BIT i table not long enough for DAC load " + "detection comparison table\n"); + return -EINVAL; + } + + daccmpoffset = ROM16(bios->data[bitentry->offset + 13]); + + /* doesn't exist on g80 */ + if (!daccmpoffset) + return 0; + + /* + * The first value in the table, following the header, is the + * comparison value, the second entry is a comparison value for + * TV load detection. + */ + + dacver = bios->data[daccmpoffset]; + dacheaderlen = bios->data[daccmpoffset + 1]; + + if (dacver != 0x00 && dacver != 0x10) { + NV_WARN(dev, "DAC load detection comparison table version " + "%d.%d not known\n", dacver >> 4, dacver & 0xf); + return -ENOSYS; + } + + bios->dactestval = ROM32(bios->data[daccmpoffset + dacheaderlen]); + bios->tvdactestval = ROM32(bios->data[daccmpoffset + dacheaderlen + 4]); + + return 0; +} + +static int parse_bit_lvds_tbl_entry(struct drm_device *dev, struct nvbios *bios, struct bit_entry *bitentry) +{ + /* + * Parses the LVDS table segment that the bit entry points to. + * Starting at bitentry->offset: + * + * offset + 0 (16 bits): LVDS strap xlate table pointer + */ + + if (bitentry->length != 2) { + NV_ERROR(dev, "Do not understand BIT LVDS table\n"); + return -EINVAL; + } + + /* + * No idea if it's still called the LVDS manufacturer table, but + * the concept's close enough. + */ + bios->fp.lvdsmanufacturerpointer = ROM16(bios->data[bitentry->offset]); + + return 0; +} + +static int +parse_bit_M_tbl_entry(struct drm_device *dev, struct nvbios *bios, + struct bit_entry *bitentry) +{ + /* + * offset + 2 (8 bits): number of options in an + * INIT_RAM_RESTRICT_ZM_REG_GROUP opcode option set + * offset + 3 (16 bits): pointer to strap xlate table for RAM + * restrict option selection + * + * There's a bunch of bits in this table other than the RAM restrict + * stuff that we don't use - their use currently unknown + */ + + /* + * Older bios versions don't have a sufficiently long table for + * what we want + */ + if (bitentry->length < 0x5) + return 0; + + if (bitentry->version < 2) { + bios->ram_restrict_group_count = bios->data[bitentry->offset + 2]; + bios->ram_restrict_tbl_ptr = ROM16(bios->data[bitentry->offset + 3]); + } else { + bios->ram_restrict_group_count = bios->data[bitentry->offset + 0]; + bios->ram_restrict_tbl_ptr = ROM16(bios->data[bitentry->offset + 1]); + } + + return 0; +} + +static int parse_bit_tmds_tbl_entry(struct drm_device *dev, struct nvbios *bios, struct bit_entry *bitentry) +{ + /* + * Parses the pointer to the TMDS table + * + * Starting at bitentry->offset: + * + * offset + 0 (16 bits): TMDS table pointer + * + * The TMDS table is typically found just before the DCB table, with a + * characteristic signature of 0x11,0x13 (1.1 being version, 0x13 being + * length?) + * + * At offset +7 is a pointer to a script, which I don't know how to + * run yet. + * At offset +9 is a pointer to another script, likewise + * Offset +11 has a pointer to a table where the first word is a pxclk + * frequency and the second word a pointer to a script, which should be + * run if the comparison pxclk frequency is less than the pxclk desired. + * This repeats for decreasing comparison frequencies + * Offset +13 has a pointer to a similar table + * The selection of table (and possibly +7/+9 script) is dictated by + * "or" from the DCB. + */ + + uint16_t tmdstableptr, script1, script2; + + if (bitentry->length != 2) { + NV_ERROR(dev, "Do not understand BIT TMDS table\n"); + return -EINVAL; + } + + tmdstableptr = ROM16(bios->data[bitentry->offset]); + if (!tmdstableptr) { + NV_ERROR(dev, "Pointer to TMDS table invalid\n"); + return -EINVAL; + } + + NV_INFO(dev, "TMDS table version %d.%d\n", + bios->data[tmdstableptr] >> 4, bios->data[tmdstableptr] & 0xf); + + /* nv50+ has v2.0, but we don't parse it atm */ + if (bios->data[tmdstableptr] != 0x11) + return -ENOSYS; + + /* + * These two scripts are odd: they don't seem to get run even when + * they are not stubbed. + */ + script1 = ROM16(bios->data[tmdstableptr + 7]); + script2 = ROM16(bios->data[tmdstableptr + 9]); + if (bios->data[script1] != 'q' || bios->data[script2] != 'q') + NV_WARN(dev, "TMDS table script pointers not stubbed\n"); + + bios->tmds.output0_script_ptr = ROM16(bios->data[tmdstableptr + 11]); + bios->tmds.output1_script_ptr = ROM16(bios->data[tmdstableptr + 13]); + + return 0; +} + +static int +parse_bit_U_tbl_entry(struct drm_device *dev, struct nvbios *bios, + struct bit_entry *bitentry) +{ + /* + * Parses the pointer to the G80 output script tables + * + * Starting at bitentry->offset: + * + * offset + 0 (16 bits): output script table pointer + */ + + uint16_t outputscripttableptr; + + if (bitentry->length != 3) { + NV_ERROR(dev, "Do not understand BIT U table\n"); + return -EINVAL; + } + + outputscripttableptr = ROM16(bios->data[bitentry->offset]); + bios->display.script_table_ptr = outputscripttableptr; + return 0; +} + +static int +parse_bit_displayport_tbl_entry(struct drm_device *dev, struct nvbios *bios, + struct bit_entry *bitentry) +{ + bios->display.dp_table_ptr = ROM16(bios->data[bitentry->offset]); + return 0; +} + +struct bit_table { + const char id; + int (* const parse_fn)(struct drm_device *, struct nvbios *, struct bit_entry *); +}; + +#define BIT_TABLE(id, funcid) ((struct bit_table){ id, parse_bit_##funcid##_tbl_entry }) + +int +bit_table(struct drm_device *dev, u8 id, struct bit_entry *bit) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + u8 entries, *entry; + + entries = bios->data[bios->offset + 10]; + entry = &bios->data[bios->offset + 12]; + while (entries--) { + if (entry[0] == id) { + bit->id = entry[0]; + bit->version = entry[1]; + bit->length = ROM16(entry[2]); + bit->offset = ROM16(entry[4]); + bit->data = ROMPTR(bios, entry[4]); + return 0; + } + + entry += bios->data[bios->offset + 9]; + } + + return -ENOENT; +} + +static int +parse_bit_table(struct nvbios *bios, const uint16_t bitoffset, + struct bit_table *table) +{ + struct drm_device *dev = bios->dev; + struct bit_entry bitentry; + + if (bit_table(dev, table->id, &bitentry) == 0) + return table->parse_fn(dev, bios, &bitentry); + + NV_INFO(dev, "BIT table '%c' not found\n", table->id); + return -ENOSYS; +} + +static int +parse_bit_structure(struct nvbios *bios, const uint16_t bitoffset) +{ + int ret; + + /* + * The only restriction on parsing order currently is having 'i' first + * for use of bios->*_version or bios->feature_byte while parsing; + * functions shouldn't be actually *doing* anything apart from pulling + * data from the image into the bios struct, thus no interdependencies + */ + ret = parse_bit_table(bios, bitoffset, &BIT_TABLE('i', i)); + if (ret) /* info? */ + return ret; + if (bios->major_version >= 0x60) /* g80+ */ + parse_bit_table(bios, bitoffset, &BIT_TABLE('A', A)); + ret = parse_bit_table(bios, bitoffset, &BIT_TABLE('C', C)); + if (ret) + return ret; + parse_bit_table(bios, bitoffset, &BIT_TABLE('D', display)); + ret = parse_bit_table(bios, bitoffset, &BIT_TABLE('I', init)); + if (ret) + return ret; + parse_bit_table(bios, bitoffset, &BIT_TABLE('M', M)); /* memory? */ + parse_bit_table(bios, bitoffset, &BIT_TABLE('L', lvds)); + parse_bit_table(bios, bitoffset, &BIT_TABLE('T', tmds)); + parse_bit_table(bios, bitoffset, &BIT_TABLE('U', U)); + parse_bit_table(bios, bitoffset, &BIT_TABLE('d', displayport)); + + return 0; +} + +static int parse_bmp_structure(struct drm_device *dev, struct nvbios *bios, unsigned int offset) +{ + /* + * Parses the BMP structure for useful things, but does not act on them + * + * offset + 5: BMP major version + * offset + 6: BMP minor version + * offset + 9: BMP feature byte + * offset + 10: BCD encoded BIOS version + * + * offset + 18: init script table pointer (for bios versions < 5.10h) + * offset + 20: extra init script table pointer (for bios + * versions < 5.10h) + * + * offset + 24: memory init table pointer (used on early bios versions) + * offset + 26: SDR memory sequencing setup data table + * offset + 28: DDR memory sequencing setup data table + * + * offset + 54: index of I2C CRTC pair to use for CRT output + * offset + 55: index of I2C CRTC pair to use for TV output + * offset + 56: index of I2C CRTC pair to use for flat panel output + * offset + 58: write CRTC index for I2C pair 0 + * offset + 59: read CRTC index for I2C pair 0 + * offset + 60: write CRTC index for I2C pair 1 + * offset + 61: read CRTC index for I2C pair 1 + * + * offset + 67: maximum internal PLL frequency (single stage PLL) + * offset + 71: minimum internal PLL frequency (single stage PLL) + * + * offset + 75: script table pointers, as described in + * parse_script_table_pointers + * + * offset + 89: TMDS single link output A table pointer + * offset + 91: TMDS single link output B table pointer + * offset + 95: LVDS single link output A table pointer + * offset + 105: flat panel timings table pointer + * offset + 107: flat panel strapping translation table pointer + * offset + 117: LVDS manufacturer panel config table pointer + * offset + 119: LVDS manufacturer strapping translation table pointer + * + * offset + 142: PLL limits table pointer + * + * offset + 156: minimum pixel clock for LVDS dual link + */ + + uint8_t *bmp = &bios->data[offset], bmp_version_major, bmp_version_minor; + uint16_t bmplength; + uint16_t legacy_scripts_offset, legacy_i2c_offset; + + /* load needed defaults in case we can't parse this info */ + bios->dcb.i2c[0].write = NV_CIO_CRE_DDC_WR__INDEX; + bios->dcb.i2c[0].read = NV_CIO_CRE_DDC_STATUS__INDEX; + bios->dcb.i2c[1].write = NV_CIO_CRE_DDC0_WR__INDEX; + bios->dcb.i2c[1].read = NV_CIO_CRE_DDC0_STATUS__INDEX; + bios->digital_min_front_porch = 0x4b; + bios->fmaxvco = 256000; + bios->fminvco = 128000; + bios->fp.duallink_transition_clk = 90000; + + bmp_version_major = bmp[5]; + bmp_version_minor = bmp[6]; + + NV_TRACE(dev, "BMP version %d.%d\n", + bmp_version_major, bmp_version_minor); + + /* + * Make sure that 0x36 is blank and can't be mistaken for a DCB + * pointer on early versions + */ + if (bmp_version_major < 5) + *(uint16_t *)&bios->data[0x36] = 0; + + /* + * Seems that the minor version was 1 for all major versions prior + * to 5. Version 6 could theoretically exist, but I suspect BIT + * happened instead. + */ + if ((bmp_version_major < 5 && bmp_version_minor != 1) || bmp_version_major > 5) { + NV_ERROR(dev, "You have an unsupported BMP version. " + "Please send in your bios\n"); + return -ENOSYS; + } + + if (bmp_version_major == 0) + /* nothing that's currently useful in this version */ + return 0; + else if (bmp_version_major == 1) + bmplength = 44; /* exact for 1.01 */ + else if (bmp_version_major == 2) + bmplength = 48; /* exact for 2.01 */ + else if (bmp_version_major == 3) + bmplength = 54; + /* guessed - mem init tables added in this version */ + else if (bmp_version_major == 4 || bmp_version_minor < 0x1) + /* don't know if 5.0 exists... */ + bmplength = 62; + /* guessed - BMP I2C indices added in version 4*/ + else if (bmp_version_minor < 0x6) + bmplength = 67; /* exact for 5.01 */ + else if (bmp_version_minor < 0x10) + bmplength = 75; /* exact for 5.06 */ + else if (bmp_version_minor == 0x10) + bmplength = 89; /* exact for 5.10h */ + else if (bmp_version_minor < 0x14) + bmplength = 118; /* exact for 5.11h */ + else if (bmp_version_minor < 0x24) + /* + * Not sure of version where pll limits came in; + * certainly exist by 0x24 though. + */ + /* length not exact: this is long enough to get lvds members */ + bmplength = 123; + else if (bmp_version_minor < 0x27) + /* + * Length not exact: this is long enough to get pll limit + * member + */ + bmplength = 144; + else + /* + * Length not exact: this is long enough to get dual link + * transition clock. + */ + bmplength = 158; + + /* checksum */ + if (nv_cksum(bmp, 8)) { + NV_ERROR(dev, "Bad BMP checksum\n"); + return -EINVAL; + } + + /* + * Bit 4 seems to indicate either a mobile bios or a quadro card -- + * mobile behaviour consistent (nv11+), quadro only seen nv18gl-nv36gl + * (not nv10gl), bit 5 that the flat panel tables are present, and + * bit 6 a tv bios. + */ + bios->feature_byte = bmp[9]; + + parse_bios_version(dev, bios, offset + 10); + + if (bmp_version_major < 5 || bmp_version_minor < 0x10) + bios->old_style_init = true; + legacy_scripts_offset = 18; + if (bmp_version_major < 2) + legacy_scripts_offset -= 4; + bios->init_script_tbls_ptr = ROM16(bmp[legacy_scripts_offset]); + bios->extra_init_script_tbl_ptr = ROM16(bmp[legacy_scripts_offset + 2]); + + if (bmp_version_major > 2) { /* appears in BMP 3 */ + bios->legacy.mem_init_tbl_ptr = ROM16(bmp[24]); + bios->legacy.sdr_seq_tbl_ptr = ROM16(bmp[26]); + bios->legacy.ddr_seq_tbl_ptr = ROM16(bmp[28]); + } + + legacy_i2c_offset = 0x48; /* BMP version 2 & 3 */ + if (bmplength > 61) + legacy_i2c_offset = offset + 54; + bios->legacy.i2c_indices.crt = bios->data[legacy_i2c_offset]; + bios->legacy.i2c_indices.tv = bios->data[legacy_i2c_offset + 1]; + bios->legacy.i2c_indices.panel = bios->data[legacy_i2c_offset + 2]; + if (bios->data[legacy_i2c_offset + 4]) + bios->dcb.i2c[0].write = bios->data[legacy_i2c_offset + 4]; + if (bios->data[legacy_i2c_offset + 5]) + bios->dcb.i2c[0].read = bios->data[legacy_i2c_offset + 5]; + if (bios->data[legacy_i2c_offset + 6]) + bios->dcb.i2c[1].write = bios->data[legacy_i2c_offset + 6]; + if (bios->data[legacy_i2c_offset + 7]) + bios->dcb.i2c[1].read = bios->data[legacy_i2c_offset + 7]; + + if (bmplength > 74) { + bios->fmaxvco = ROM32(bmp[67]); + bios->fminvco = ROM32(bmp[71]); + } + if (bmplength > 88) + parse_script_table_pointers(bios, offset + 75); + if (bmplength > 94) { + bios->tmds.output0_script_ptr = ROM16(bmp[89]); + bios->tmds.output1_script_ptr = ROM16(bmp[91]); + /* + * Never observed in use with lvds scripts, but is reused for + * 18/24 bit panel interface default for EDID equipped panels + * (if_is_24bit not set directly to avoid any oscillation). + */ + bios->legacy.lvds_single_a_script_ptr = ROM16(bmp[95]); + } + if (bmplength > 108) { + bios->fp.fptablepointer = ROM16(bmp[105]); + bios->fp.fpxlatetableptr = ROM16(bmp[107]); + bios->fp.xlatwidth = 1; + } + if (bmplength > 120) { + bios->fp.lvdsmanufacturerpointer = ROM16(bmp[117]); + bios->fp.fpxlatemanufacturertableptr = ROM16(bmp[119]); + } + if (bmplength > 143) + bios->pll_limit_tbl_ptr = ROM16(bmp[142]); + + if (bmplength > 157) + bios->fp.duallink_transition_clk = ROM16(bmp[156]) * 10; + + return 0; +} + +static uint16_t findstr(uint8_t *data, int n, const uint8_t *str, int len) +{ + int i, j; + + for (i = 0; i <= (n - len); i++) { + for (j = 0; j < len; j++) + if (data[i + j] != str[j]) + break; + if (j == len) + return i; + } + + return 0; +} + +static struct dcb_gpio_entry * +new_gpio_entry(struct nvbios *bios) +{ + struct drm_device *dev = bios->dev; + struct dcb_gpio_table *gpio = &bios->dcb.gpio; + + if (gpio->entries >= DCB_MAX_NUM_GPIO_ENTRIES) { + NV_ERROR(dev, "exceeded maximum number of gpio entries!!\n"); + return NULL; + } + + return &gpio->entry[gpio->entries++]; +} + +struct dcb_gpio_entry * +nouveau_bios_gpio_entry(struct drm_device *dev, enum dcb_gpio_tag tag) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + int i; + + for (i = 0; i < bios->dcb.gpio.entries; i++) { + if (bios->dcb.gpio.entry[i].tag != tag) + continue; + + return &bios->dcb.gpio.entry[i]; + } + + return NULL; +} + +static void +parse_dcb_gpio_table(struct nvbios *bios) +{ + struct drm_device *dev = bios->dev; + struct dcb_gpio_entry *e; + u8 headerlen, entries, recordlen; + u8 *dcb, *gpio = NULL, *entry; + int i; + + dcb = ROMPTR(bios, bios->data[0x36]); + if (dcb[0] >= 0x30) { + gpio = ROMPTR(bios, dcb[10]); + if (!gpio) + goto no_table; + + headerlen = gpio[1]; + entries = gpio[2]; + recordlen = gpio[3]; + } else + if (dcb[0] >= 0x22 && dcb[-1] >= 0x13) { + gpio = ROMPTR(bios, dcb[-15]); + if (!gpio) + goto no_table; + + headerlen = 3; + entries = gpio[2]; + recordlen = gpio[1]; + } else + if (dcb[0] >= 0x22) { + /* No GPIO table present, parse the TVDAC GPIO data. */ + uint8_t *tvdac_gpio = &dcb[-5]; + + if (tvdac_gpio[0] & 1) { + e = new_gpio_entry(bios); + e->tag = DCB_GPIO_TVDAC0; + e->line = tvdac_gpio[1] >> 4; + e->invert = tvdac_gpio[0] & 2; + } + + goto no_table; + } else { + NV_DEBUG(dev, "no/unknown gpio table on DCB 0x%02x\n", dcb[0]); + goto no_table; + } + + entry = gpio + headerlen; + for (i = 0; i < entries; i++, entry += recordlen) { + e = new_gpio_entry(bios); + if (!e) + break; + + if (gpio[0] < 0x40) { + e->entry = ROM16(entry[0]); + e->tag = (e->entry & 0x07e0) >> 5; + if (e->tag == 0x3f) { + bios->dcb.gpio.entries--; + continue; + } + + e->line = (e->entry & 0x001f); + e->invert = ((e->entry & 0xf800) >> 11) != 4; + } else { + e->entry = ROM32(entry[0]); + e->tag = (e->entry & 0x0000ff00) >> 8; + if (e->tag == 0xff) { + bios->dcb.gpio.entries--; + continue; + } + + e->line = (e->entry & 0x0000001f) >> 0; + e->state_default = (e->entry & 0x01000000) >> 24; + e->state[0] = (e->entry & 0x18000000) >> 27; + e->state[1] = (e->entry & 0x60000000) >> 29; + } + } + +no_table: + /* Apple iMac G4 NV18 */ + if (nv_match_device(dev, 0x0189, 0x10de, 0x0010)) { + e = new_gpio_entry(bios); + if (e) { + e->tag = DCB_GPIO_TVDAC0; + e->line = 4; + } + } +} + +struct dcb_connector_table_entry * +nouveau_bios_connector_entry(struct drm_device *dev, int index) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + struct dcb_connector_table_entry *cte; + + if (index >= bios->dcb.connector.entries) + return NULL; + + cte = &bios->dcb.connector.entry[index]; + if (cte->type == 0xff) + return NULL; + + return cte; +} + +static enum dcb_connector_type +divine_connector_type(struct nvbios *bios, int index) +{ + struct dcb_table *dcb = &bios->dcb; + unsigned encoders = 0, type = DCB_CONNECTOR_NONE; + int i; + + for (i = 0; i < dcb->entries; i++) { + if (dcb->entry[i].connector == index) + encoders |= (1 << dcb->entry[i].type); + } + + if (encoders & (1 << OUTPUT_DP)) { + if (encoders & (1 << OUTPUT_TMDS)) + type = DCB_CONNECTOR_DP; + else + type = DCB_CONNECTOR_eDP; + } else + if (encoders & (1 << OUTPUT_TMDS)) { + if (encoders & (1 << OUTPUT_ANALOG)) + type = DCB_CONNECTOR_DVI_I; + else + type = DCB_CONNECTOR_DVI_D; + } else + if (encoders & (1 << OUTPUT_ANALOG)) { + type = DCB_CONNECTOR_VGA; + } else + if (encoders & (1 << OUTPUT_LVDS)) { + type = DCB_CONNECTOR_LVDS; + } else + if (encoders & (1 << OUTPUT_TV)) { + type = DCB_CONNECTOR_TV_0; + } + + return type; +} + +static void +apply_dcb_connector_quirks(struct nvbios *bios, int idx) +{ + struct dcb_connector_table_entry *cte = &bios->dcb.connector.entry[idx]; + struct drm_device *dev = bios->dev; + + /* Gigabyte NX85T */ + if (nv_match_device(dev, 0x0421, 0x1458, 0x344c)) { + if (cte->type == DCB_CONNECTOR_HDMI_1) + cte->type = DCB_CONNECTOR_DVI_I; + } +} + +static void +parse_dcb_connector_table(struct nvbios *bios) +{ + struct drm_device *dev = bios->dev; + struct dcb_connector_table *ct = &bios->dcb.connector; + struct dcb_connector_table_entry *cte; + uint8_t *conntab = &bios->data[bios->dcb.connector_table_ptr]; + uint8_t *entry; + int i; + + if (!bios->dcb.connector_table_ptr) { + NV_DEBUG_KMS(dev, "No DCB connector table present\n"); + return; + } + + NV_INFO(dev, "DCB connector table: VHER 0x%02x %d %d %d\n", + conntab[0], conntab[1], conntab[2], conntab[3]); + if ((conntab[0] != 0x30 && conntab[0] != 0x40) || + (conntab[3] != 2 && conntab[3] != 4)) { + NV_ERROR(dev, " Unknown! Please report.\n"); + return; + } + + ct->entries = conntab[2]; + + entry = conntab + conntab[1]; + cte = &ct->entry[0]; + for (i = 0; i < conntab[2]; i++, entry += conntab[3], cte++) { + cte->index = i; + if (conntab[3] == 2) + cte->entry = ROM16(entry[0]); + else + cte->entry = ROM32(entry[0]); + + cte->type = (cte->entry & 0x000000ff) >> 0; + cte->index2 = (cte->entry & 0x00000f00) >> 8; + switch (cte->entry & 0x00033000) { + case 0x00001000: + cte->gpio_tag = 0x07; + break; + case 0x00002000: + cte->gpio_tag = 0x08; + break; + case 0x00010000: + cte->gpio_tag = 0x51; + break; + case 0x00020000: + cte->gpio_tag = 0x52; + break; + default: + cte->gpio_tag = 0xff; + break; + } + + if (cte->type == 0xff) + continue; + + apply_dcb_connector_quirks(bios, i); + + NV_INFO(dev, " %d: 0x%08x: type 0x%02x idx %d tag 0x%02x\n", + i, cte->entry, cte->type, cte->index, cte->gpio_tag); + + /* check for known types, fallback to guessing the type + * from attached encoders if we hit an unknown. + */ + switch (cte->type) { + case DCB_CONNECTOR_VGA: + case DCB_CONNECTOR_TV_0: + case DCB_CONNECTOR_TV_1: + case DCB_CONNECTOR_TV_3: + case DCB_CONNECTOR_DVI_I: + case DCB_CONNECTOR_DVI_D: + case DCB_CONNECTOR_LVDS: + case DCB_CONNECTOR_DP: + case DCB_CONNECTOR_eDP: + case DCB_CONNECTOR_HDMI_0: + case DCB_CONNECTOR_HDMI_1: + break; + default: + cte->type = divine_connector_type(bios, cte->index); + NV_WARN(dev, "unknown type, using 0x%02x\n", cte->type); + break; + } + + if (nouveau_override_conntype) { + int type = divine_connector_type(bios, cte->index); + if (type != cte->type) + NV_WARN(dev, " -> type 0x%02x\n", cte->type); + } + } +} + +static struct dcb_entry *new_dcb_entry(struct dcb_table *dcb) +{ + struct dcb_entry *entry = &dcb->entry[dcb->entries]; + + memset(entry, 0, sizeof(struct dcb_entry)); + entry->index = dcb->entries++; + + return entry; +} + +static void fabricate_vga_output(struct dcb_table *dcb, int i2c, int heads) +{ + struct dcb_entry *entry = new_dcb_entry(dcb); + + entry->type = 0; + entry->i2c_index = i2c; + entry->heads = heads; + entry->location = DCB_LOC_ON_CHIP; + entry->or = 1; +} + +static void fabricate_dvi_i_output(struct dcb_table *dcb, bool twoHeads) +{ + struct dcb_entry *entry = new_dcb_entry(dcb); + + entry->type = 2; + entry->i2c_index = LEGACY_I2C_PANEL; + entry->heads = twoHeads ? 3 : 1; + entry->location = !DCB_LOC_ON_CHIP; /* ie OFF CHIP */ + entry->or = 1; /* means |0x10 gets set on CRE_LCD__INDEX */ + entry->duallink_possible = false; /* SiI164 and co. are single link */ + +#if 0 + /* + * For dvi-a either crtc probably works, but my card appears to only + * support dvi-d. "nvidia" still attempts to program it for dvi-a, + * doing the full fp output setup (program 0x6808.. fp dimension regs, + * setting 0x680848 to 0x10000111 to enable, maybe setting 0x680880); + * the monitor picks up the mode res ok and lights up, but no pixel + * data appears, so the board manufacturer probably connected up the + * sync lines, but missed the video traces / components + * + * with this introduction, dvi-a left as an exercise for the reader. + */ + fabricate_vga_output(dcb, LEGACY_I2C_PANEL, entry->heads); +#endif +} + +static void fabricate_tv_output(struct dcb_table *dcb, bool twoHeads) +{ + struct dcb_entry *entry = new_dcb_entry(dcb); + + entry->type = 1; + entry->i2c_index = LEGACY_I2C_TV; + entry->heads = twoHeads ? 3 : 1; + entry->location = !DCB_LOC_ON_CHIP; /* ie OFF CHIP */ +} + +static bool +parse_dcb20_entry(struct drm_device *dev, struct dcb_table *dcb, + uint32_t conn, uint32_t conf, struct dcb_entry *entry) +{ + entry->type = conn & 0xf; + entry->i2c_index = (conn >> 4) & 0xf; + entry->heads = (conn >> 8) & 0xf; + if (dcb->version >= 0x40) + entry->connector = (conn >> 12) & 0xf; + entry->bus = (conn >> 16) & 0xf; + entry->location = (conn >> 20) & 0x3; + entry->or = (conn >> 24) & 0xf; + + switch (entry->type) { + case OUTPUT_ANALOG: + /* + * Although the rest of a CRT conf dword is usually + * zeros, mac biosen have stuff there so we must mask + */ + entry->crtconf.maxfreq = (dcb->version < 0x30) ? + (conf & 0xffff) * 10 : + (conf & 0xff) * 10000; + break; + case OUTPUT_LVDS: + { + uint32_t mask; + if (conf & 0x1) + entry->lvdsconf.use_straps_for_mode = true; + if (dcb->version < 0x22) { + mask = ~0xd; + /* + * The laptop in bug 14567 lies and claims to not use + * straps when it does, so assume all DCB 2.0 laptops + * use straps, until a broken EDID using one is produced + */ + entry->lvdsconf.use_straps_for_mode = true; + /* + * Both 0x4 and 0x8 show up in v2.0 tables; assume they + * mean the same thing (probably wrong, but might work) + */ + if (conf & 0x4 || conf & 0x8) + entry->lvdsconf.use_power_scripts = true; + } else { + mask = ~0x7; + if (conf & 0x2) + entry->lvdsconf.use_acpi_for_edid = true; + if (conf & 0x4) + entry->lvdsconf.use_power_scripts = true; + entry->lvdsconf.sor.link = (conf & 0x00000030) >> 4; + } + if (conf & mask) { + /* + * Until we even try to use these on G8x, it's + * useless reporting unknown bits. They all are. + */ + if (dcb->version >= 0x40) + break; + + NV_ERROR(dev, "Unknown LVDS configuration bits, " + "please report\n"); + } + break; + } + case OUTPUT_TV: + { + if (dcb->version >= 0x30) + entry->tvconf.has_component_output = conf & (0x8 << 4); + else + entry->tvconf.has_component_output = false; + + break; + } + case OUTPUT_DP: + entry->dpconf.sor.link = (conf & 0x00000030) >> 4; + entry->dpconf.link_bw = (conf & 0x00e00000) >> 21; + switch ((conf & 0x0f000000) >> 24) { + case 0xf: + entry->dpconf.link_nr = 4; + break; + case 0x3: + entry->dpconf.link_nr = 2; + break; + default: + entry->dpconf.link_nr = 1; + break; + } + break; + case OUTPUT_TMDS: + if (dcb->version >= 0x40) + entry->tmdsconf.sor.link = (conf & 0x00000030) >> 4; + else if (dcb->version >= 0x30) + entry->tmdsconf.slave_addr = (conf & 0x00000700) >> 8; + else if (dcb->version >= 0x22) + entry->tmdsconf.slave_addr = (conf & 0x00000070) >> 4; + + break; + case OUTPUT_EOL: + /* weird g80 mobile type that "nv" treats as a terminator */ + dcb->entries--; + return false; + default: + break; + } + + if (dcb->version < 0x40) { + /* Normal entries consist of a single bit, but dual link has + * the next most significant bit set too + */ + entry->duallink_possible = + ((1 << (ffs(entry->or) - 1)) * 3 == entry->or); + } else { + entry->duallink_possible = (entry->sorconf.link == 3); + } + + /* unsure what DCB version introduces this, 3.0? */ + if (conf & 0x100000) + entry->i2c_upper_default = true; + + return true; +} + +static bool +parse_dcb15_entry(struct drm_device *dev, struct dcb_table *dcb, + uint32_t conn, uint32_t conf, struct dcb_entry *entry) +{ + switch (conn & 0x0000000f) { + case 0: + entry->type = OUTPUT_ANALOG; + break; + case 1: + entry->type = OUTPUT_TV; + break; + case 2: + case 4: + if (conn & 0x10) + entry->type = OUTPUT_LVDS; + else + entry->type = OUTPUT_TMDS; + break; + case 3: + entry->type = OUTPUT_LVDS; + break; + default: + NV_ERROR(dev, "Unknown DCB type %d\n", conn & 0x0000000f); + return false; + } + + entry->i2c_index = (conn & 0x0003c000) >> 14; + entry->heads = ((conn & 0x001c0000) >> 18) + 1; + entry->or = entry->heads; /* same as heads, hopefully safe enough */ + entry->location = (conn & 0x01e00000) >> 21; + entry->bus = (conn & 0x0e000000) >> 25; + entry->duallink_possible = false; + + switch (entry->type) { + case OUTPUT_ANALOG: + entry->crtconf.maxfreq = (conf & 0xffff) * 10; + break; + case OUTPUT_TV: + entry->tvconf.has_component_output = false; + break; + case OUTPUT_LVDS: + if ((conn & 0x00003f00) != 0x10) + entry->lvdsconf.use_straps_for_mode = true; + entry->lvdsconf.use_power_scripts = true; + break; + default: + break; + } + + return true; +} + +static bool parse_dcb_entry(struct drm_device *dev, struct dcb_table *dcb, + uint32_t conn, uint32_t conf) +{ + struct dcb_entry *entry = new_dcb_entry(dcb); + bool ret; + + if (dcb->version >= 0x20) + ret = parse_dcb20_entry(dev, dcb, conn, conf, entry); + else + ret = parse_dcb15_entry(dev, dcb, conn, conf, entry); + if (!ret) + return ret; + + read_dcb_i2c_entry(dev, dcb->version, dcb->i2c_table, + entry->i2c_index, &dcb->i2c[entry->i2c_index]); + + return true; +} + +static +void merge_like_dcb_entries(struct drm_device *dev, struct dcb_table *dcb) +{ + /* + * DCB v2.0 lists each output combination separately. + * Here we merge compatible entries to have fewer outputs, with + * more options + */ + + int i, newentries = 0; + + for (i = 0; i < dcb->entries; i++) { + struct dcb_entry *ient = &dcb->entry[i]; + int j; + + for (j = i + 1; j < dcb->entries; j++) { + struct dcb_entry *jent = &dcb->entry[j]; + + if (jent->type == 100) /* already merged entry */ + continue; + + /* merge heads field when all other fields the same */ + if (jent->i2c_index == ient->i2c_index && + jent->type == ient->type && + jent->location == ient->location && + jent->or == ient->or) { + NV_TRACE(dev, "Merging DCB entries %d and %d\n", + i, j); + ient->heads |= jent->heads; + jent->type = 100; /* dummy value */ + } + } + } + + /* Compact entries merged into others out of dcb */ + for (i = 0; i < dcb->entries; i++) { + if (dcb->entry[i].type == 100) + continue; + + if (newentries != i) { + dcb->entry[newentries] = dcb->entry[i]; + dcb->entry[newentries].index = newentries; + } + newentries++; + } + + dcb->entries = newentries; +} + +static bool +apply_dcb_encoder_quirks(struct drm_device *dev, int idx, u32 *conn, u32 *conf) +{ + /* Dell Precision M6300 + * DCB entry 2: 02025312 00000010 + * DCB entry 3: 02026312 00000020 + * + * Identical, except apparently a different connector on a + * different SOR link. Not a clue how we're supposed to know + * which one is in use if it even shares an i2c line... + * + * Ignore the connector on the second SOR link to prevent + * nasty problems until this is sorted (assuming it's not a + * VBIOS bug). + */ + if (nv_match_device(dev, 0x040d, 0x1028, 0x019b)) { + if (*conn == 0x02026312 && *conf == 0x00000020) + return false; + } + + return true; +} + +static int +parse_dcb_table(struct drm_device *dev, struct nvbios *bios, bool twoHeads) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct dcb_table *dcb = &bios->dcb; + uint16_t dcbptr = 0, i2ctabptr = 0; + uint8_t *dcbtable; + uint8_t headerlen = 0x4, entries = DCB_MAX_NUM_ENTRIES; + bool configblock = true; + int recordlength = 8, confofs = 4; + int i; + + /* get the offset from 0x36 */ + if (dev_priv->card_type > NV_04) { + dcbptr = ROM16(bios->data[0x36]); + if (dcbptr == 0x0000) + NV_WARN(dev, "No output data (DCB) found in BIOS\n"); + } + + /* this situation likely means a really old card, pre DCB */ + if (dcbptr == 0x0) { + NV_INFO(dev, "Assuming a CRT output exists\n"); + fabricate_vga_output(dcb, LEGACY_I2C_CRT, 1); + + if (nv04_tv_identify(dev, bios->legacy.i2c_indices.tv) >= 0) + fabricate_tv_output(dcb, twoHeads); + + return 0; + } + + dcbtable = &bios->data[dcbptr]; + + /* get DCB version */ + dcb->version = dcbtable[0]; + NV_TRACE(dev, "Found Display Configuration Block version %d.%d\n", + dcb->version >> 4, dcb->version & 0xf); + + if (dcb->version >= 0x20) { /* NV17+ */ + uint32_t sig; + + if (dcb->version >= 0x30) { /* NV40+ */ + headerlen = dcbtable[1]; + entries = dcbtable[2]; + recordlength = dcbtable[3]; + i2ctabptr = ROM16(dcbtable[4]); + sig = ROM32(dcbtable[6]); + dcb->gpio_table_ptr = ROM16(dcbtable[10]); + dcb->connector_table_ptr = ROM16(dcbtable[20]); + } else { + i2ctabptr = ROM16(dcbtable[2]); + sig = ROM32(dcbtable[4]); + headerlen = 8; + } + + if (sig != 0x4edcbdcb) { + NV_ERROR(dev, "Bad Display Configuration Block " + "signature (%08X)\n", sig); + return -EINVAL; + } + } else if (dcb->version >= 0x15) { /* some NV11 and NV20 */ + char sig[8] = { 0 }; + + strncpy(sig, (char *)&dcbtable[-7], 7); + i2ctabptr = ROM16(dcbtable[2]); + recordlength = 10; + confofs = 6; + + if (strcmp(sig, "DEV_REC")) { + NV_ERROR(dev, "Bad Display Configuration Block " + "signature (%s)\n", sig); + return -EINVAL; + } + } else { + /* + * v1.4 (some NV15/16, NV11+) seems the same as v1.5, but always + * has the same single (crt) entry, even when tv-out present, so + * the conclusion is this version cannot really be used. + * v1.2 tables (some NV6/10, and NV15+) normally have the same + * 5 entries, which are not specific to the card and so no use. + * v1.2 does have an I2C table that read_dcb_i2c_table can + * handle, but cards exist (nv11 in #14821) with a bad i2c table + * pointer, so use the indices parsed in parse_bmp_structure. + * v1.1 (NV5+, maybe some NV4) is entirely unhelpful + */ + NV_TRACEWARN(dev, "No useful information in BIOS output table; " + "adding all possible outputs\n"); + fabricate_vga_output(dcb, LEGACY_I2C_CRT, 1); + + /* + * Attempt to detect TV before DVI because the test + * for the former is more accurate and it rules the + * latter out. + */ + if (nv04_tv_identify(dev, + bios->legacy.i2c_indices.tv) >= 0) + fabricate_tv_output(dcb, twoHeads); + + else if (bios->tmds.output0_script_ptr || + bios->tmds.output1_script_ptr) + fabricate_dvi_i_output(dcb, twoHeads); + + return 0; + } + + if (!i2ctabptr) + NV_WARN(dev, "No pointer to DCB I2C port table\n"); + else { + dcb->i2c_table = &bios->data[i2ctabptr]; + if (dcb->version >= 0x30) + dcb->i2c_default_indices = dcb->i2c_table[4]; + + /* + * Parse the "management" I2C bus, used for hardware + * monitoring and some external TMDS transmitters. + */ + if (dcb->version >= 0x22) { + int idx = (dcb->version >= 0x40 ? + dcb->i2c_default_indices & 0xf : + 2); + + read_dcb_i2c_entry(dev, dcb->version, dcb->i2c_table, + idx, &dcb->i2c[idx]); + } + } + + if (entries > DCB_MAX_NUM_ENTRIES) + entries = DCB_MAX_NUM_ENTRIES; + + for (i = 0; i < entries; i++) { + uint32_t connection, config = 0; + + connection = ROM32(dcbtable[headerlen + recordlength * i]); + if (configblock) + config = ROM32(dcbtable[headerlen + confofs + recordlength * i]); + + /* seen on an NV11 with DCB v1.5 */ + if (connection == 0x00000000) + break; + + /* seen on an NV17 with DCB v2.0 */ + if (connection == 0xffffffff) + break; + + if ((connection & 0x0000000f) == 0x0000000f) + continue; + + if (!apply_dcb_encoder_quirks(dev, i, &connection, &config)) + continue; + + NV_TRACEWARN(dev, "Raw DCB entry %d: %08x %08x\n", + dcb->entries, connection, config); + + if (!parse_dcb_entry(dev, dcb, connection, config)) + break; + } + + /* + * apart for v2.1+ not being known for requiring merging, this + * guarantees dcbent->index is the index of the entry in the rom image + */ + if (dcb->version < 0x21) + merge_like_dcb_entries(dev, dcb); + + if (!dcb->entries) + return -ENXIO; + + parse_dcb_gpio_table(bios); + parse_dcb_connector_table(bios); + return 0; +} + +static void +fixup_legacy_connector(struct nvbios *bios) +{ + struct dcb_table *dcb = &bios->dcb; + int i, i2c, i2c_conn[DCB_MAX_NUM_I2C_ENTRIES] = { }; + + /* + * DCB 3.0 also has the table in most cases, but there are some cards + * where the table is filled with stub entries, and the DCB entriy + * indices are all 0. We don't need the connector indices on pre-G80 + * chips (yet?) so limit the use to DCB 4.0 and above. + */ + if (dcb->version >= 0x40) + return; + + dcb->connector.entries = 0; + + /* + * No known connector info before v3.0, so make it up. the rule here + * is: anything on the same i2c bus is considered to be on the same + * connector. any output without an associated i2c bus is assigned + * its own unique connector index. + */ + for (i = 0; i < dcb->entries; i++) { + /* + * Ignore the I2C index for on-chip TV-out, as there + * are cards with bogus values (nv31m in bug 23212), + * and it's otherwise useless. + */ + if (dcb->entry[i].type == OUTPUT_TV && + dcb->entry[i].location == DCB_LOC_ON_CHIP) + dcb->entry[i].i2c_index = 0xf; + i2c = dcb->entry[i].i2c_index; + + if (i2c_conn[i2c]) { + dcb->entry[i].connector = i2c_conn[i2c] - 1; + continue; + } + + dcb->entry[i].connector = dcb->connector.entries++; + if (i2c != 0xf) + i2c_conn[i2c] = dcb->connector.entries; + } + + /* Fake the connector table as well as just connector indices */ + for (i = 0; i < dcb->connector.entries; i++) { + dcb->connector.entry[i].index = i; + dcb->connector.entry[i].type = divine_connector_type(bios, i); + dcb->connector.entry[i].gpio_tag = 0xff; + } +} + +static void +fixup_legacy_i2c(struct nvbios *bios) +{ + struct dcb_table *dcb = &bios->dcb; + int i; + + for (i = 0; i < dcb->entries; i++) { + if (dcb->entry[i].i2c_index == LEGACY_I2C_CRT) + dcb->entry[i].i2c_index = bios->legacy.i2c_indices.crt; + if (dcb->entry[i].i2c_index == LEGACY_I2C_PANEL) + dcb->entry[i].i2c_index = bios->legacy.i2c_indices.panel; + if (dcb->entry[i].i2c_index == LEGACY_I2C_TV) + dcb->entry[i].i2c_index = bios->legacy.i2c_indices.tv; + } +} + +static int load_nv17_hwsq_ucode_entry(struct drm_device *dev, struct nvbios *bios, uint16_t hwsq_offset, int entry) +{ + /* + * The header following the "HWSQ" signature has the number of entries, + * and the entry size + * + * An entry consists of a dword to write to the sequencer control reg + * (0x00001304), followed by the ucode bytes, written sequentially, + * starting at reg 0x00001400 + */ + + uint8_t bytes_to_write; + uint16_t hwsq_entry_offset; + int i; + + if (bios->data[hwsq_offset] <= entry) { + NV_ERROR(dev, "Too few entries in HW sequencer table for " + "requested entry\n"); + return -ENOENT; + } + + bytes_to_write = bios->data[hwsq_offset + 1]; + + if (bytes_to_write != 36) { + NV_ERROR(dev, "Unknown HW sequencer entry size\n"); + return -EINVAL; + } + + NV_TRACE(dev, "Loading NV17 power sequencing microcode\n"); + + hwsq_entry_offset = hwsq_offset + 2 + entry * bytes_to_write; + + /* set sequencer control */ + bios_wr32(bios, 0x00001304, ROM32(bios->data[hwsq_entry_offset])); + bytes_to_write -= 4; + + /* write ucode */ + for (i = 0; i < bytes_to_write; i += 4) + bios_wr32(bios, 0x00001400 + i, ROM32(bios->data[hwsq_entry_offset + i + 4])); + + /* twiddle NV_PBUS_DEBUG_4 */ + bios_wr32(bios, NV_PBUS_DEBUG_4, bios_rd32(bios, NV_PBUS_DEBUG_4) | 0x18); + + return 0; +} + +static int load_nv17_hw_sequencer_ucode(struct drm_device *dev, + struct nvbios *bios) +{ + /* + * BMP based cards, from NV17, need a microcode loading to correctly + * control the GPIO etc for LVDS panels + * + * BIT based cards seem to do this directly in the init scripts + * + * The microcode entries are found by the "HWSQ" signature. + */ + + const uint8_t hwsq_signature[] = { 'H', 'W', 'S', 'Q' }; + const int sz = sizeof(hwsq_signature); + int hwsq_offset; + + hwsq_offset = findstr(bios->data, bios->length, hwsq_signature, sz); + if (!hwsq_offset) + return 0; + + /* always use entry 0? */ + return load_nv17_hwsq_ucode_entry(dev, bios, hwsq_offset + sz, 0); +} + +uint8_t *nouveau_bios_embedded_edid(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + const uint8_t edid_sig[] = { + 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00 }; + uint16_t offset = 0; + uint16_t newoffset; + int searchlen = NV_PROM_SIZE; + + if (bios->fp.edid) + return bios->fp.edid; + + while (searchlen) { + newoffset = findstr(&bios->data[offset], searchlen, + edid_sig, 8); + if (!newoffset) + return NULL; + offset += newoffset; + if (!nv_cksum(&bios->data[offset], EDID1_LEN)) + break; + + searchlen -= offset; + offset++; + } + + NV_TRACE(dev, "Found EDID in BIOS\n"); + + return bios->fp.edid = &bios->data[offset]; +} + +void +nouveau_bios_run_init_table(struct drm_device *dev, uint16_t table, + struct dcb_entry *dcbent) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + struct init_exec iexec = { true, false }; + + mutex_lock(&bios->lock); + bios->display.output = dcbent; + parse_init_table(bios, table, &iexec); + bios->display.output = NULL; + mutex_unlock(&bios->lock); +} + +static bool NVInitVBIOS(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + + memset(bios, 0, sizeof(struct nvbios)); + mutex_init(&bios->lock); + bios->dev = dev; + + if (!NVShadowVBIOS(dev, bios->data)) + return false; + + bios->length = NV_PROM_SIZE; + return true; +} + +static int nouveau_parse_vbios_struct(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + const uint8_t bit_signature[] = { 0xff, 0xb8, 'B', 'I', 'T' }; + const uint8_t bmp_signature[] = { 0xff, 0x7f, 'N', 'V', 0x0 }; + int offset; + + offset = findstr(bios->data, bios->length, + bit_signature, sizeof(bit_signature)); + if (offset) { + NV_TRACE(dev, "BIT BIOS found\n"); + bios->type = NVBIOS_BIT; + bios->offset = offset; + return parse_bit_structure(bios, offset + 6); + } + + offset = findstr(bios->data, bios->length, + bmp_signature, sizeof(bmp_signature)); + if (offset) { + NV_TRACE(dev, "BMP BIOS found\n"); + bios->type = NVBIOS_BMP; + bios->offset = offset; + return parse_bmp_structure(dev, bios, offset); + } + + NV_ERROR(dev, "No known BIOS signature found\n"); + return -ENODEV; +} + +int +nouveau_run_vbios_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + int i, ret = 0; + + /* Reset the BIOS head to 0. */ + bios->state.crtchead = 0; + + if (bios->major_version < 5) /* BMP only */ + load_nv17_hw_sequencer_ucode(dev, bios); + + if (bios->execute) { + bios->fp.last_script_invoc = 0; + bios->fp.lvds_init_run = false; + } + + parse_init_tables(bios); + + /* + * Runs some additional script seen on G8x VBIOSen. The VBIOS' + * parser will run this right after the init tables, the binary + * driver appears to run it at some point later. + */ + if (bios->some_script_ptr) { + struct init_exec iexec = {true, false}; + + NV_INFO(dev, "Parsing VBIOS init table at offset 0x%04X\n", + bios->some_script_ptr); + parse_init_table(bios, bios->some_script_ptr, &iexec); + } + + if (dev_priv->card_type >= NV_50) { + for (i = 0; i < bios->dcb.entries; i++) { + nouveau_bios_run_display_table(dev, + &bios->dcb.entry[i], + 0, 0); + } + } + + return ret; +} + +static void +nouveau_bios_i2c_devices_takedown(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + struct dcb_i2c_entry *entry; + int i; + + entry = &bios->dcb.i2c[0]; + for (i = 0; i < DCB_MAX_NUM_I2C_ENTRIES; i++, entry++) + nouveau_i2c_fini(dev, entry); +} + +static bool +nouveau_bios_posted(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + unsigned htotal; + + if (dev_priv->chipset >= NV_50) { + if (NVReadVgaCrtc(dev, 0, 0x00) == 0 && + NVReadVgaCrtc(dev, 0, 0x1a) == 0) + return false; + return true; + } + if (nouveau_force_post) + bios->execute = true; + + htotal = NVReadVgaCrtc(dev, 0, 0x06); + htotal |= (NVReadVgaCrtc(dev, 0, 0x07) & 0x01) << 8; + htotal |= (NVReadVgaCrtc(dev, 0, 0x07) & 0x20) << 4; + htotal |= (NVReadVgaCrtc(dev, 0, 0x25) & 0x01) << 10; + htotal |= (NVReadVgaCrtc(dev, 0, 0x41) & 0x01) << 11; + + return (htotal != 0); +} + +int +nouveau_bios_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + int ret; + + if (!NVInitVBIOS(dev)) + return -ENODEV; + + ret = nouveau_parse_vbios_struct(dev); + if (ret) + return ret; + + ret = parse_dcb_table(dev, bios, nv_two_heads(dev)); + if (ret) + return ret; + + fixup_legacy_i2c(bios); + fixup_legacy_connector(bios); + + if (!bios->major_version) /* we don't run version 0 bios */ + return 0; + + /* init script execution disabled */ + bios->execute = false; + + /* ... unless card isn't POSTed already */ + if (!nouveau_bios_posted(dev)) { + NV_INFO(dev, "Adaptor not initialised, " + "running VBIOS init tables.\n"); + bios->execute = true; + } + if (nouveau_force_post) + bios->execute = true; + + ret = nouveau_run_vbios_init(dev); + if (ret) + return ret; + + /* feature_byte on BMP is poor, but init always sets CR4B */ + if (bios->major_version < 5) + bios->is_mobile = NVReadVgaCrtc(dev, 0, NV_CIO_CRE_4B) & 0x40; + + /* all BIT systems need p_f_m_t for digital_min_front_porch */ + if (bios->is_mobile || bios->major_version >= 5) + ret = parse_fp_mode_table(dev, bios); + + /* allow subsequent scripts to execute */ + bios->execute = true; + + return 0; +} + +void +nouveau_bios_takedown(struct drm_device *dev) +{ + nouveau_bios_i2c_devices_takedown(dev); +} diff --git a/driver/pscnv/nouveau_bios.h b/driver/pscnv/nouveau_bios.h new file mode 100644 index 00000000..50a648e0 --- /dev/null +++ b/driver/pscnv/nouveau_bios.h @@ -0,0 +1,335 @@ +/* + * Copyright 2007-2008 Nouveau Project + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +#ifndef __NOUVEAU_BIOS_H__ +#define __NOUVEAU_BIOS_H__ + +#include "nvreg.h" +#include "nouveau_i2c.h" + +#define DCB_MAX_NUM_ENTRIES 16 +#define DCB_MAX_NUM_I2C_ENTRIES 16 +#define DCB_MAX_NUM_GPIO_ENTRIES 32 +#define DCB_MAX_NUM_CONNECTOR_ENTRIES 16 + +#define DCB_LOC_ON_CHIP 0 + +#define ROM16(x) le16_to_cpu(*(uint16_t *)&(x)) +#define ROM32(x) le32_to_cpu(*(uint32_t *)&(x)) +#define ROMPTR(bios, x) (ROM16(x) ? &(bios)->data[ROM16(x)] : NULL) + +struct bit_entry { + uint8_t id; + uint8_t version; + uint16_t length; + uint16_t offset; + uint8_t *data; +}; + +int bit_table(struct drm_device *, u8 id, struct bit_entry *); + +struct dcb_i2c_entry { + uint32_t entry; + uint8_t port_type; + uint8_t read, write; + struct nouveau_i2c_chan *chan; +}; + +enum dcb_gpio_tag { + DCB_GPIO_TVDAC0 = 0xc, + DCB_GPIO_TVDAC1 = 0x2d, +}; + +struct dcb_gpio_entry { + enum dcb_gpio_tag tag; + int line; + bool invert; + uint32_t entry; + uint8_t state_default; + uint8_t state[2]; +}; + +struct dcb_gpio_table { + int entries; + struct dcb_gpio_entry entry[DCB_MAX_NUM_GPIO_ENTRIES]; +}; + +enum dcb_connector_type { + DCB_CONNECTOR_VGA = 0x00, + DCB_CONNECTOR_TV_0 = 0x10, + DCB_CONNECTOR_TV_1 = 0x11, + DCB_CONNECTOR_TV_3 = 0x13, + DCB_CONNECTOR_DVI_I = 0x30, + DCB_CONNECTOR_DVI_D = 0x31, + DCB_CONNECTOR_LVDS = 0x40, + DCB_CONNECTOR_DP = 0x46, + DCB_CONNECTOR_eDP = 0x47, + DCB_CONNECTOR_HDMI_0 = 0x60, + DCB_CONNECTOR_HDMI_1 = 0x61, + DCB_CONNECTOR_NONE = 0xff +}; + +struct dcb_connector_table_entry { + uint8_t index; + uint32_t entry; + enum dcb_connector_type type; + uint8_t index2; + uint8_t gpio_tag; + void *drm; +}; + +struct dcb_connector_table { + int entries; + struct dcb_connector_table_entry entry[DCB_MAX_NUM_CONNECTOR_ENTRIES]; +}; + +enum dcb_type { + OUTPUT_ANALOG = 0, + OUTPUT_TV = 1, + OUTPUT_TMDS = 2, + OUTPUT_LVDS = 3, + OUTPUT_DP = 6, + OUTPUT_EOL = 14, /* DCB 4.0+, appears to be end-of-list */ + OUTPUT_ANY = -1 +}; + +struct dcb_entry { + int index; /* may not be raw dcb index if merging has happened */ + enum dcb_type type; + uint8_t i2c_index; + uint8_t heads; + uint8_t connector; + uint8_t bus; + uint8_t location; + uint8_t or; + bool duallink_possible; + union { + struct sor_conf { + int link; + } sorconf; + struct { + int maxfreq; + } crtconf; + struct { + struct sor_conf sor; + bool use_straps_for_mode; + bool use_acpi_for_edid; + bool use_power_scripts; + } lvdsconf; + struct { + bool has_component_output; + } tvconf; + struct { + struct sor_conf sor; + int link_nr; + int link_bw; + } dpconf; + struct { + struct sor_conf sor; + int slave_addr; + } tmdsconf; + }; + bool i2c_upper_default; +}; + +struct dcb_table { + uint8_t version; + + int entries; + struct dcb_entry entry[DCB_MAX_NUM_ENTRIES]; + + uint8_t *i2c_table; + uint8_t i2c_default_indices; + struct dcb_i2c_entry i2c[DCB_MAX_NUM_I2C_ENTRIES]; + + uint16_t gpio_table_ptr; + struct dcb_gpio_table gpio; + uint16_t connector_table_ptr; + struct dcb_connector_table connector; +}; + +enum nouveau_or { + OUTPUT_A = (1 << 0), + OUTPUT_B = (1 << 1), + OUTPUT_C = (1 << 2) +}; + +enum LVDS_script { + /* Order *does* matter here */ + LVDS_INIT = 1, + LVDS_RESET, + LVDS_BACKLIGHT_ON, + LVDS_BACKLIGHT_OFF, + LVDS_PANEL_ON, + LVDS_PANEL_OFF +}; + +/* these match types in pll limits table version 0x40, + * nouveau uses them on all chipsets internally where a + * specific pll needs to be referenced, but the exact + * register isn't known. + */ +enum pll_types { + PLL_CORE = 0x01, + PLL_SHADER = 0x02, + PLL_UNK03 = 0x03, + PLL_MEMORY = 0x04, + PLL_UNK05 = 0x05, + PLL_UNK40 = 0x40, + PLL_UNK41 = 0x41, + PLL_UNK42 = 0x42, + PLL_VPLL0 = 0x80, + PLL_VPLL1 = 0x81, + PLL_MAX = 0xff +}; + +struct pll_lims { + u32 reg; + + struct { + int minfreq; + int maxfreq; + int min_inputfreq; + int max_inputfreq; + + uint8_t min_m; + uint8_t max_m; + uint8_t min_n; + uint8_t max_n; + } vco1, vco2; + + uint8_t max_log2p; + /* + * for most pre nv50 cards setting a log2P of 7 (the common max_log2p + * value) is no different to 6 (at least for vplls) so allowing the MNP + * calc to use 7 causes the generated clock to be out by a factor of 2. + * however, max_log2p cannot be fixed-up during parsing as the + * unmodified max_log2p value is still needed for setting mplls, hence + * an additional max_usable_log2p member + */ + uint8_t max_usable_log2p; + uint8_t log2p_bias; + + uint8_t min_p; + uint8_t max_p; + + int refclk; +}; + +struct nvbios { + struct drm_device *dev; + enum { + NVBIOS_BMP, + NVBIOS_BIT + } type; + uint16_t offset; + + uint8_t chip_version; + + uint32_t dactestval; + uint32_t tvdactestval; + uint8_t digital_min_front_porch; + bool fp_no_ddc; + + struct mutex lock; + + uint8_t data[NV_PROM_SIZE]; + unsigned int length; + bool execute; + + uint8_t major_version; + uint8_t feature_byte; + bool is_mobile; + + uint32_t fmaxvco, fminvco; + + bool old_style_init; + uint16_t init_script_tbls_ptr; + uint16_t extra_init_script_tbl_ptr; + uint16_t macro_index_tbl_ptr; + uint16_t macro_tbl_ptr; + uint16_t condition_tbl_ptr; + uint16_t io_condition_tbl_ptr; + uint16_t io_flag_condition_tbl_ptr; + uint16_t init_function_tbl_ptr; + + uint16_t pll_limit_tbl_ptr; + uint16_t ram_restrict_tbl_ptr; + uint8_t ram_restrict_group_count; + + uint16_t some_script_ptr; /* BIT I + 14 */ + uint16_t init96_tbl_ptr; /* BIT I + 16 */ + + struct dcb_table dcb; + + struct { + int crtchead; + } state; + + struct { + struct dcb_entry *output; + uint16_t script_table_ptr; + uint16_t dp_table_ptr; + } display; + + struct { + uint16_t fptablepointer; /* also used by tmds */ + uint16_t fpxlatetableptr; + int xlatwidth; + uint16_t lvdsmanufacturerpointer; + uint16_t fpxlatemanufacturertableptr; + uint16_t mode_ptr; + uint16_t xlated_entry; + bool power_off_for_reset; + bool reset_after_pclk_change; + bool dual_link; + bool link_c_increment; + bool if_is_24bit; + int duallink_transition_clk; + uint8_t strapless_is_24bit; + uint8_t *edid; + + /* will need resetting after suspend */ + int last_script_invoc; + bool lvds_init_run; + } fp; + + struct { + uint16_t output0_script_ptr; + uint16_t output1_script_ptr; + } tmds; + + struct { + uint16_t mem_init_tbl_ptr; + uint16_t sdr_seq_tbl_ptr; + uint16_t ddr_seq_tbl_ptr; + + struct { + uint8_t crt, tv, panel; + } i2c_indices; + + uint16_t lvds_single_a_script_ptr; + } legacy; +}; + +#endif diff --git a/driver/pscnv/nouveau_calc.c b/driver/pscnv/nouveau_calc.c new file mode 100644 index 00000000..ed6ef507 --- /dev/null +++ b/driver/pscnv/nouveau_calc.c @@ -0,0 +1,477 @@ +/* + * Copyright 1993-2003 NVIDIA, Corporation + * Copyright 2007-2009 Stuart Bennett + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF + * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_hw.h" +#include "nouveau_reg.h" + +/****************************************************************************\ +* * +* The video arbitration routines calculate some "magic" numbers. Fixes * +* the snow seen when accessing the framebuffer without it. * +* It just works (I hope). * +* * +\****************************************************************************/ + +struct nv_fifo_info { + int lwm; + int burst; +}; + +struct nv_sim_state { + int pclk_khz; + int mclk_khz; + int nvclk_khz; + int bpp; + int mem_page_miss; + int mem_latency; + int memory_type; + int memory_width; + int two_heads; +}; + +static void +nv04_calc_arb(struct nv_fifo_info *fifo, struct nv_sim_state *arb) +{ + int pagemiss, cas, bpp; + int nvclks, mclks, crtpagemiss; + int found, mclk_extra, mclk_loop, cbs, m1, p1; + int mclk_freq, pclk_freq, nvclk_freq; + int us_m, us_n, us_p, crtc_drain_rate; + int cpm_us, us_crt, clwm; + + pclk_freq = arb->pclk_khz; + mclk_freq = arb->mclk_khz; + nvclk_freq = arb->nvclk_khz; + pagemiss = arb->mem_page_miss; + cas = arb->mem_latency; + bpp = arb->bpp; + cbs = 128; + + nvclks = 10; + mclks = 13 + cas; + mclk_extra = 3; + found = 0; + + while (!found) { + found = 1; + + mclk_loop = mclks + mclk_extra; + us_m = mclk_loop * 1000 * 1000 / mclk_freq; + us_n = nvclks * 1000 * 1000 / nvclk_freq; + us_p = nvclks * 1000 * 1000 / pclk_freq; + + crtc_drain_rate = pclk_freq * bpp / 8; + crtpagemiss = 2; + crtpagemiss += 1; + cpm_us = crtpagemiss * pagemiss * 1000 * 1000 / mclk_freq; + us_crt = cpm_us + us_m + us_n + us_p; + clwm = us_crt * crtc_drain_rate / (1000 * 1000); + clwm++; + + m1 = clwm + cbs - 512; + p1 = m1 * pclk_freq / mclk_freq; + p1 = p1 * bpp / 8; + if ((p1 < m1 && m1 > 0) || clwm > 519) { + found = !mclk_extra; + mclk_extra--; + } + if (clwm < 384) + clwm = 384; + + fifo->lwm = clwm; + fifo->burst = cbs; + } +} + +static void +nv10_calc_arb(struct nv_fifo_info *fifo, struct nv_sim_state *arb) +{ + int fill_rate, drain_rate; + int pclks, nvclks, mclks, xclks; + int pclk_freq, nvclk_freq, mclk_freq; + int fill_lat, extra_lat; + int max_burst_o, max_burst_l; + int fifo_len, min_lwm, max_lwm; + const int burst_lat = 80; /* Maximum allowable latency due + * to the CRTC FIFO burst. (ns) */ + + pclk_freq = arb->pclk_khz; + nvclk_freq = arb->nvclk_khz; + mclk_freq = arb->mclk_khz; + + fill_rate = mclk_freq * arb->memory_width / 8; /* kB/s */ + drain_rate = pclk_freq * arb->bpp / 8; /* kB/s */ + + fifo_len = arb->two_heads ? 1536 : 1024; /* B */ + + /* Fixed FIFO refill latency. */ + + pclks = 4; /* lwm detect. */ + + nvclks = 3 /* lwm -> sync. */ + + 2 /* fbi bus cycles (1 req + 1 busy) */ + + 1 /* 2 edge sync. may be very close to edge so + * just put one. */ + + 1 /* fbi_d_rdv_n */ + + 1 /* Fbi_d_rdata */ + + 1; /* crtfifo load */ + + mclks = 1 /* 2 edge sync. may be very close to edge so + * just put one. */ + + 1 /* arb_hp_req */ + + 5 /* tiling pipeline */ + + 2 /* latency fifo */ + + 2 /* memory request to fbio block */ + + 7; /* data returned from fbio block */ + + /* Need to accumulate 256 bits for read */ + mclks += (arb->memory_type == 0 ? 2 : 1) + * arb->memory_width / 32; + + fill_lat = mclks * 1000 * 1000 / mclk_freq /* minimum mclk latency */ + + nvclks * 1000 * 1000 / nvclk_freq /* nvclk latency */ + + pclks * 1000 * 1000 / pclk_freq; /* pclk latency */ + + /* Conditional FIFO refill latency. */ + + xclks = 2 * arb->mem_page_miss + mclks /* Extra latency due to + * the overlay. */ + + 2 * arb->mem_page_miss /* Extra pagemiss latency. */ + + (arb->bpp == 32 ? 8 : 4); /* Margin of error. */ + + extra_lat = xclks * 1000 * 1000 / mclk_freq; + + if (arb->two_heads) + /* Account for another CRTC. */ + extra_lat += fill_lat + extra_lat + burst_lat; + + /* FIFO burst */ + + /* Max burst not leading to overflows. */ + max_burst_o = (1 + fifo_len - extra_lat * drain_rate / (1000 * 1000)) + * (fill_rate / 1000) / ((fill_rate - drain_rate) / 1000); + fifo->burst = min(max_burst_o, 1024); + + /* Max burst value with an acceptable latency. */ + max_burst_l = burst_lat * fill_rate / (1000 * 1000); + fifo->burst = min(max_burst_l, fifo->burst); + + fifo->burst = rounddown_pow_of_two(fifo->burst); + + /* FIFO low watermark */ + + min_lwm = (fill_lat + extra_lat) * drain_rate / (1000 * 1000) + 1; + max_lwm = fifo_len - fifo->burst + + fill_lat * drain_rate / (1000 * 1000) + + fifo->burst * drain_rate / fill_rate; + + fifo->lwm = min_lwm + 10 * (max_lwm - min_lwm) / 100; /* Empirical. */ +} + +static void +nv04_update_arb(struct drm_device *dev, int VClk, int bpp, + int *burst, int *lwm) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv_fifo_info fifo_data; + struct nv_sim_state sim_data; + int MClk = nouveau_hw_get_clock(dev, PLL_MEMORY); + int NVClk = nouveau_hw_get_clock(dev, PLL_CORE); + uint32_t cfg1 = nvReadFB(dev, NV04_PFB_CFG1); + + sim_data.pclk_khz = VClk; + sim_data.mclk_khz = MClk; + sim_data.nvclk_khz = NVClk; + sim_data.bpp = bpp; + sim_data.two_heads = nv_two_heads(dev); + if ((dev->pci_device & 0xffff) == 0x01a0 /*CHIPSET_NFORCE*/ || + (dev->pci_device & 0xffff) == 0x01f0 /*CHIPSET_NFORCE2*/) { + uint32_t type; + + pci_read_config_dword(pci_get_bus_and_slot(0, 1), 0x7c, &type); + + sim_data.memory_type = (type >> 12) & 1; + sim_data.memory_width = 64; + sim_data.mem_latency = 3; + sim_data.mem_page_miss = 10; + } else { + sim_data.memory_type = nvReadFB(dev, NV04_PFB_CFG0) & 0x1; + sim_data.memory_width = (nvReadEXTDEV(dev, NV_PEXTDEV_BOOT_0) & 0x10) ? 128 : 64; + sim_data.mem_latency = cfg1 & 0xf; + sim_data.mem_page_miss = ((cfg1 >> 4) & 0xf) + ((cfg1 >> 31) & 0x1); + } + + if (dev_priv->card_type == NV_04) + nv04_calc_arb(&fifo_data, &sim_data); + else + nv10_calc_arb(&fifo_data, &sim_data); + + *burst = ilog2(fifo_data.burst >> 4); + *lwm = fifo_data.lwm >> 3; +} + +static void +nv20_update_arb(int *burst, int *lwm) +{ + unsigned int fifo_size, burst_size, graphics_lwm; + + fifo_size = 2048; + burst_size = 512; + graphics_lwm = fifo_size - burst_size; + + *burst = ilog2(burst_size >> 5); + *lwm = graphics_lwm >> 3; +} + +void +nouveau_calc_arb(struct drm_device *dev, int vclk, int bpp, int *burst, int *lwm) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + if (dev_priv->card_type < NV_20) + nv04_update_arb(dev, vclk, bpp, burst, lwm); + else if ((dev->pci_device & 0xfff0) == 0x0240 /*CHIPSET_C51*/ || + (dev->pci_device & 0xfff0) == 0x03d0 /*CHIPSET_C512*/) { + *burst = 128; + *lwm = 0x0480; + } else + nv20_update_arb(burst, lwm); +} + +static int +getMNP_single(struct drm_device *dev, struct pll_lims *pll_lim, int clk, + struct nouveau_pll_vals *bestpv) +{ + /* Find M, N and P for a single stage PLL + * + * Note that some bioses (NV3x) have lookup tables of precomputed MNP + * values, but we're too lazy to use those atm + * + * "clk" parameter in kHz + * returns calculated clock + */ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int cv = dev_priv->vbios.chip_version; + int minvco = pll_lim->vco1.minfreq, maxvco = pll_lim->vco1.maxfreq; + int minM = pll_lim->vco1.min_m, maxM = pll_lim->vco1.max_m; + int minN = pll_lim->vco1.min_n, maxN = pll_lim->vco1.max_n; + int minU = pll_lim->vco1.min_inputfreq; + int maxU = pll_lim->vco1.max_inputfreq; + int minP = pll_lim->max_p ? pll_lim->min_p : 0; + int maxP = pll_lim->max_p ? pll_lim->max_p : pll_lim->max_usable_log2p; + int crystal = pll_lim->refclk; + int M, N, thisP, P; + int clkP, calcclk; + int delta, bestdelta = INT_MAX; + int bestclk = 0; + + /* this division verified for nv20, nv18, nv28 (Haiku), and nv34 */ + /* possibly correlated with introduction of 27MHz crystal */ + if (dev_priv->card_type < NV_50) { + if (cv < 0x17 || cv == 0x1a || cv == 0x20) { + if (clk > 250000) + maxM = 6; + if (clk > 340000) + maxM = 2; + } else if (cv < 0x40) { + if (clk > 150000) + maxM = 6; + if (clk > 200000) + maxM = 4; + if (clk > 340000) + maxM = 2; + } + } + + P = pll_lim->max_p ? maxP : (1 << maxP); + if ((clk * P) < minvco) { + minvco = clk * maxP; + maxvco = minvco * 2; + } + + if (clk + clk/200 > maxvco) /* +0.5% */ + maxvco = clk + clk/200; + + /* NV34 goes maxlog2P->0, NV20 goes 0->maxlog2P */ + for (thisP = minP; thisP <= maxP; thisP++) { + P = pll_lim->max_p ? thisP : (1 << thisP); + clkP = clk * P; + + if (clkP < minvco) + continue; + if (clkP > maxvco) + return bestclk; + + for (M = minM; M <= maxM; M++) { + if (crystal/M < minU) + return bestclk; + if (crystal/M > maxU) + continue; + + /* add crystal/2 to round better */ + N = (clkP * M + crystal/2) / crystal; + + if (N < minN) + continue; + if (N > maxN) + break; + + /* more rounding additions */ + calcclk = ((N * crystal + P/2) / P + M/2) / M; + delta = abs(calcclk - clk); + /* we do an exhaustive search rather than terminating + * on an optimality condition... + */ + if (delta < bestdelta) { + bestdelta = delta; + bestclk = calcclk; + bestpv->N1 = N; + bestpv->M1 = M; + bestpv->log2P = thisP; + if (delta == 0) /* except this one */ + return bestclk; + } + } + } + + return bestclk; +} + +static int +getMNP_double(struct drm_device *dev, struct pll_lims *pll_lim, int clk, + struct nouveau_pll_vals *bestpv) +{ + /* Find M, N and P for a two stage PLL + * + * Note that some bioses (NV30+) have lookup tables of precomputed MNP + * values, but we're too lazy to use those atm + * + * "clk" parameter in kHz + * returns calculated clock + */ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int chip_version = dev_priv->vbios.chip_version; + int minvco1 = pll_lim->vco1.minfreq, maxvco1 = pll_lim->vco1.maxfreq; + int minvco2 = pll_lim->vco2.minfreq, maxvco2 = pll_lim->vco2.maxfreq; + int minU1 = pll_lim->vco1.min_inputfreq, minU2 = pll_lim->vco2.min_inputfreq; + int maxU1 = pll_lim->vco1.max_inputfreq, maxU2 = pll_lim->vco2.max_inputfreq; + int minM1 = pll_lim->vco1.min_m, maxM1 = pll_lim->vco1.max_m; + int minN1 = pll_lim->vco1.min_n, maxN1 = pll_lim->vco1.max_n; + int minM2 = pll_lim->vco2.min_m, maxM2 = pll_lim->vco2.max_m; + int minN2 = pll_lim->vco2.min_n, maxN2 = pll_lim->vco2.max_n; + int maxlog2P = pll_lim->max_usable_log2p; + int crystal = pll_lim->refclk; + bool fixedgain2 = (minM2 == maxM2 && minN2 == maxN2); + int M1, N1, M2, N2, log2P; + int clkP, calcclk1, calcclk2, calcclkout; + int delta, bestdelta = INT_MAX; + int bestclk = 0; + + int vco2 = (maxvco2 - maxvco2/200) / 2; + for (log2P = 0; clk && log2P < maxlog2P && clk <= (vco2 >> log2P); log2P++) + ; + clkP = clk << log2P; + + if (maxvco2 < clk + clk/200) /* +0.5% */ + maxvco2 = clk + clk/200; + + for (M1 = minM1; M1 <= maxM1; M1++) { + if (crystal/M1 < minU1) + return bestclk; + if (crystal/M1 > maxU1) + continue; + + for (N1 = minN1; N1 <= maxN1; N1++) { + calcclk1 = crystal * N1 / M1; + if (calcclk1 < minvco1) + continue; + if (calcclk1 > maxvco1) + break; + + for (M2 = minM2; M2 <= maxM2; M2++) { + if (calcclk1/M2 < minU2) + break; + if (calcclk1/M2 > maxU2) + continue; + + /* add calcclk1/2 to round better */ + N2 = (clkP * M2 + calcclk1/2) / calcclk1; + if (N2 < minN2) + continue; + if (N2 > maxN2) + break; + + if (!fixedgain2) { + if (chip_version < 0x60) + if (N2/M2 < 4 || N2/M2 > 10) + continue; + + calcclk2 = calcclk1 * N2 / M2; + if (calcclk2 < minvco2) + break; + if (calcclk2 > maxvco2) + continue; + } else + calcclk2 = calcclk1; + + calcclkout = calcclk2 >> log2P; + delta = abs(calcclkout - clk); + /* we do an exhaustive search rather than terminating + * on an optimality condition... + */ + if (delta < bestdelta) { + bestdelta = delta; + bestclk = calcclkout; + bestpv->N1 = N1; + bestpv->M1 = M1; + bestpv->N2 = N2; + bestpv->M2 = M2; + bestpv->log2P = log2P; + if (delta == 0) /* except this one */ + return bestclk; + } + } + } + } + + return bestclk; +} + +int +nouveau_calc_pll_mnp(struct drm_device *dev, struct pll_lims *pll_lim, int clk, + struct nouveau_pll_vals *pv) +{ + int outclk; + + if (!pll_lim->vco2.maxfreq) + outclk = getMNP_single(dev, pll_lim, clk, pv); + else + outclk = getMNP_double(dev, pll_lim, clk, pv); + + if (!outclk) + NV_ERROR(dev, "Could not find a compatible set of PLL values\n"); + + return outclk; +} diff --git a/driver/pscnv/nouveau_connector.c b/driver/pscnv/nouveau_connector.c new file mode 100644 index 00000000..3bcea925 --- /dev/null +++ b/driver/pscnv/nouveau_connector.c @@ -0,0 +1,945 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include + +#include "drmP.h" +#include "drm_edid.h" +#include "drm_crtc_helper.h" + +#include "nouveau_reg.h" +#include "nouveau_drv.h" +#include "nouveau_encoder.h" +#include "nouveau_crtc.h" +#include "nouveau_connector.h" +#include "nouveau_hw.h" +#include "pscnv_kapi.h" + +static struct nouveau_encoder * +find_encoder_by_type(struct drm_connector *connector, int type) +{ + struct drm_device *dev = connector->dev; + struct nouveau_encoder *nv_encoder; + struct drm_mode_object *obj; + int i, id; + + for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) { + id = connector->encoder_ids[i]; + if (!id) + break; + + obj = drm_mode_object_find(dev, id, DRM_MODE_OBJECT_ENCODER); + if (!obj) + continue; + nv_encoder = nouveau_encoder(obj_to_encoder(obj)); + + if (type == OUTPUT_ANY || nv_encoder->dcb->type == type) + return nv_encoder; + } + + return NULL; +} + +struct nouveau_connector * +nouveau_encoder_connector_get(struct nouveau_encoder *encoder) +{ + struct drm_device *dev = to_drm_encoder(encoder)->dev; + struct drm_connector *drm_connector; + + list_for_each_entry(drm_connector, &dev->mode_config.connector_list, head) { + if (drm_connector->encoder == to_drm_encoder(encoder)) + return nouveau_connector(drm_connector); + } + + return NULL; +} + +/*TODO: This could use improvement, and learn to handle the fixed + * BIOS tables etc. It's fine currently, for its only user. + */ +int +nouveau_connector_bpp(struct drm_connector *connector) +{ + struct nouveau_connector *nv_connector = nouveau_connector(connector); + + if (nv_connector->edid && nv_connector->edid->revision >= 4) { + u8 bpc = ((nv_connector->edid->input & 0x70) >> 3) + 4; + if (bpc > 4) + return bpc; + } + + return 18; +} + +static void +nouveau_connector_destroy(struct drm_connector *drm_connector) +{ + struct nouveau_connector *nv_connector = + nouveau_connector(drm_connector); + struct drm_device *dev; + + if (!nv_connector) + return; + + dev = nv_connector->base.dev; + NV_DEBUG_KMS(dev, "\n"); + + kfree(nv_connector->edid); + drm_sysfs_connector_remove(drm_connector); + drm_connector_cleanup(drm_connector); + kfree(drm_connector); +} + +static struct nouveau_i2c_chan * +nouveau_connector_ddc_detect(struct drm_connector *connector, + struct nouveau_encoder **pnv_encoder) +{ + struct drm_device *dev = connector->dev; + int i; + + for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) { + struct nouveau_i2c_chan *i2c = NULL; + struct nouveau_encoder *nv_encoder; + struct drm_mode_object *obj; + int id; + + id = connector->encoder_ids[i]; + if (!id) + break; + + obj = drm_mode_object_find(dev, id, DRM_MODE_OBJECT_ENCODER); + if (!obj) + continue; + nv_encoder = nouveau_encoder(obj_to_encoder(obj)); + + if (nv_encoder->dcb->i2c_index < 0xf) + i2c = nouveau_i2c_find(dev, nv_encoder->dcb->i2c_index); + + if (i2c && nouveau_probe_i2c_addr(i2c, 0x50)) { + *pnv_encoder = nv_encoder; + return i2c; + } + } + + return NULL; +} + +static struct nouveau_encoder * +nouveau_connector_of_detect(struct drm_connector *connector) +{ +#ifdef __powerpc__ + struct drm_device *dev = connector->dev; + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct nouveau_encoder *nv_encoder; + struct device_node *cn, *dn = pci_device_to_OF_node(dev->pdev); + + if (!dn || + !((nv_encoder = find_encoder_by_type(connector, OUTPUT_TMDS)) || + (nv_encoder = find_encoder_by_type(connector, OUTPUT_ANALOG)))) + return NULL; + + for_each_child_of_node(dn, cn) { + const char *name = of_get_property(cn, "name", NULL); + const void *edid = of_get_property(cn, "EDID", NULL); + int idx = name ? name[strlen(name) - 1] - 'A' : 0; + + if (nv_encoder->dcb->i2c_index == idx && edid) { + nv_connector->edid = + kmemdup(edid, EDID_LENGTH, GFP_KERNEL); + of_node_put(cn); + return nv_encoder; + } + } +#endif + return NULL; +} + +static void +nouveau_connector_set_encoder(struct drm_connector *connector, + struct nouveau_encoder *nv_encoder) +{ + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct drm_nouveau_private *dev_priv = connector->dev->dev_private; + struct drm_device *dev = connector->dev; + + if (nv_connector->detected_encoder == nv_encoder) + return; + nv_connector->detected_encoder = nv_encoder; + + if (nv_encoder->dcb->type == OUTPUT_LVDS || + nv_encoder->dcb->type == OUTPUT_TMDS) { + connector->doublescan_allowed = false; + connector->interlace_allowed = false; + } else { + connector->doublescan_allowed = true; + if (dev_priv->card_type == NV_20 || + (dev_priv->card_type == NV_10 && + (dev->pci_device & 0x0ff0) != 0x0100 && + (dev->pci_device & 0x0ff0) != 0x0150)) + /* HW is broken */ + connector->interlace_allowed = false; + else + connector->interlace_allowed = true; + } + + if (nv_connector->dcb->type == DCB_CONNECTOR_DVI_I) { + drm_connector_property_set_value(connector, + dev->mode_config.dvi_i_subconnector_property, + nv_encoder->dcb->type == OUTPUT_TMDS ? + DRM_MODE_SUBCONNECTOR_DVID : + DRM_MODE_SUBCONNECTOR_DVIA); + } +} + +static enum drm_connector_status +#ifdef PSCNV_KAPI_DRM_CONNECTOR_DETECT_1 +nouveau_connector_detect(struct drm_connector *connector) +#else +#ifdef PSCNV_KAPI_DRM_CONNECTOR_DETECT_2 +nouveau_connector_detect(struct drm_connector *connector, bool force) +#else +#error cannot determine drm_connector.detect API +#endif +#endif +{ + struct drm_device *dev = connector->dev; + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct nouveau_encoder *nv_encoder = NULL; + struct nouveau_i2c_chan *i2c; + int type; + + /* Cleanup the previous EDID block. */ + if (nv_connector->edid) { + drm_mode_connector_update_edid_property(connector, NULL); + kfree(nv_connector->edid); + nv_connector->edid = NULL; + } + + i2c = nouveau_connector_ddc_detect(connector, &nv_encoder); + if (i2c) { + nv_connector->edid = drm_get_edid(connector, &i2c->adapter); + drm_mode_connector_update_edid_property(connector, + nv_connector->edid); + if (!nv_connector->edid) { + NV_ERROR(dev, "DDC responded, but no EDID for %s\n", + drm_get_connector_name(connector)); + goto detect_analog; + } + + if (nv_encoder->dcb->type == OUTPUT_DP && + !nouveau_dp_detect(to_drm_encoder(nv_encoder))) { + NV_ERROR(dev, "Detected %s, but failed init\n", + drm_get_connector_name(connector)); + return connector_status_disconnected; + } + + /* Override encoder type for DVI-I based on whether EDID + * says the display is digital or analog, both use the + * same i2c channel so the value returned from ddc_detect + * isn't necessarily correct. + */ + if (nv_connector->dcb->type == DCB_CONNECTOR_DVI_I) { + if (nv_connector->edid->input & DRM_EDID_INPUT_DIGITAL) + type = OUTPUT_TMDS; + else + type = OUTPUT_ANALOG; + + nv_encoder = find_encoder_by_type(connector, type); + if (!nv_encoder) { + NV_ERROR(dev, "Detected %d encoder on %s, " + "but no object!\n", type, + drm_get_connector_name(connector)); + return connector_status_disconnected; + } + } + + nouveau_connector_set_encoder(connector, nv_encoder); + return connector_status_connected; + } + + nv_encoder = nouveau_connector_of_detect(connector); + if (nv_encoder) { + nouveau_connector_set_encoder(connector, nv_encoder); + return connector_status_connected; + } + +detect_analog: + nv_encoder = find_encoder_by_type(connector, OUTPUT_ANALOG); + if (!nv_encoder && !nouveau_tv_disable) + nv_encoder = find_encoder_by_type(connector, OUTPUT_TV); + if (nv_encoder) { + struct drm_encoder *encoder = to_drm_encoder(nv_encoder); + struct drm_encoder_helper_funcs *helper = + encoder->helper_private; + + if (helper->detect(encoder, connector) == + connector_status_connected) { + nouveau_connector_set_encoder(connector, nv_encoder); + return connector_status_connected; + } + + } + + return connector_status_disconnected; +} + +static enum drm_connector_status +#ifdef PSCNV_KAPI_DRM_CONNECTOR_DETECT_1 +nouveau_connector_detect_lvds(struct drm_connector *connector) +#else +#ifdef PSCNV_KAPI_DRM_CONNECTOR_DETECT_2 +nouveau_connector_detect_lvds(struct drm_connector *connector, bool force) +#else +#error cannot determine drm_connector.detect API +#endif +#endif +{ + struct drm_device *dev = connector->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct nouveau_encoder *nv_encoder = NULL; + enum drm_connector_status status = connector_status_disconnected; + + /* Cleanup the previous EDID block. */ + if (nv_connector->edid) { + drm_mode_connector_update_edid_property(connector, NULL); + kfree(nv_connector->edid); + nv_connector->edid = NULL; + } + + nv_encoder = find_encoder_by_type(connector, OUTPUT_LVDS); + if (!nv_encoder) + return connector_status_disconnected; + + /* Try retrieving EDID via DDC */ + if (!dev_priv->vbios.fp_no_ddc) { +#ifdef PSCNV_KAPI_DRM_CONNECTOR_DETECT_1 + status = nouveau_connector_detect(connector); +#else +#ifdef PSCNV_KAPI_DRM_CONNECTOR_DETECT_2 + status = nouveau_connector_detect(connector, force); +#else +#error cannot determine drm_connector.detect API +#endif +#endif + if (status == connector_status_connected) + goto out; + } + + /* On some laptops (Sony, i'm looking at you) there appears to + * be no direct way of accessing the panel's EDID. The only + * option available to us appears to be to ask ACPI for help.. + * + * It's important this check's before trying straps, one of the + * said manufacturer's laptops are configured in such a way + * the nouveau decides an entry in the VBIOS FP mode table is + * valid - it's not (rh#613284) + */ + if (nv_encoder->dcb->lvdsconf.use_acpi_for_edid) { + if (!nouveau_acpi_edid(dev, connector)) { + status = connector_status_connected; + goto out; + } + } + + /* If no EDID found above, and the VBIOS indicates a hardcoded + * modeline is avalilable for the panel, set it as the panel's + * native mode and exit. + */ + if (nouveau_bios_fp_mode(dev, NULL) && (dev_priv->vbios.fp_no_ddc || + nv_encoder->dcb->lvdsconf.use_straps_for_mode)) { + status = connector_status_connected; + goto out; + } + + /* Still nothing, some VBIOS images have a hardcoded EDID block + * stored for the panel stored in them. + */ + if (!dev_priv->vbios.fp_no_ddc) { + struct edid *edid = + (struct edid *)nouveau_bios_embedded_edid(dev); + if (edid) { + nv_connector->edid = kmalloc(EDID_LENGTH, GFP_KERNEL); + *(nv_connector->edid) = *edid; + status = connector_status_connected; + } + } + +out: +#if defined(CONFIG_ACPI_BUTTON) || \ + (defined(CONFIG_ACPI_BUTTON_MODULE) && defined(MODULE)) + if (status == connector_status_connected && + !nouveau_ignorelid && !acpi_lid_open()) + status = connector_status_unknown; +#endif + + drm_mode_connector_update_edid_property(connector, nv_connector->edid); + nouveau_connector_set_encoder(connector, nv_encoder); + return status; +} + +static void +nouveau_connector_force(struct drm_connector *connector) +{ + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct nouveau_encoder *nv_encoder; + int type; + + if (nv_connector->dcb->type == DCB_CONNECTOR_DVI_I) { + if (connector->force == DRM_FORCE_ON_DIGITAL) + type = OUTPUT_TMDS; + else + type = OUTPUT_ANALOG; + } else + type = OUTPUT_ANY; + + nv_encoder = find_encoder_by_type(connector, type); + if (!nv_encoder) { + NV_ERROR(connector->dev, "can't find encoder to force %s on!\n", + drm_get_connector_name(connector)); + connector->status = connector_status_disconnected; + return; + } + + nouveau_connector_set_encoder(connector, nv_encoder); +} + +static int +nouveau_connector_set_property(struct drm_connector *connector, + struct drm_property *property, uint64_t value) +{ + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct nouveau_encoder *nv_encoder = nv_connector->detected_encoder; + struct drm_encoder *encoder = to_drm_encoder(nv_encoder); + struct drm_device *dev = connector->dev; + int ret; + + /* Scaling mode */ + if (property == dev->mode_config.scaling_mode_property) { + struct nouveau_crtc *nv_crtc = NULL; + bool modeset = false; + + switch (value) { + case DRM_MODE_SCALE_NONE: + case DRM_MODE_SCALE_FULLSCREEN: + case DRM_MODE_SCALE_CENTER: + case DRM_MODE_SCALE_ASPECT: + break; + default: + return -EINVAL; + } + + /* LVDS always needs gpu scaling */ + if (nv_connector->dcb->type == DCB_CONNECTOR_LVDS && + value == DRM_MODE_SCALE_NONE) + return -EINVAL; + + /* Changing between GPU and panel scaling requires a full + * modeset + */ + if ((nv_connector->scaling_mode == DRM_MODE_SCALE_NONE) || + (value == DRM_MODE_SCALE_NONE)) + modeset = true; + nv_connector->scaling_mode = value; + + if (connector->encoder && connector->encoder->crtc) + nv_crtc = nouveau_crtc(connector->encoder->crtc); + if (!nv_crtc) + return 0; + + if (modeset || !nv_crtc->set_scale) { + ret = drm_crtc_helper_set_mode(&nv_crtc->base, + &nv_crtc->base.mode, + nv_crtc->base.x, + nv_crtc->base.y, NULL); + if (!ret) + return -EINVAL; + } else { + ret = nv_crtc->set_scale(nv_crtc, value, true); + if (ret) + return ret; + } + + return 0; + } + + /* Dithering */ + if (property == dev->mode_config.dithering_mode_property) { + struct nouveau_crtc *nv_crtc = NULL; + + if (value == DRM_MODE_DITHERING_ON) + nv_connector->use_dithering = true; + else + nv_connector->use_dithering = false; + + if (connector->encoder && connector->encoder->crtc) + nv_crtc = nouveau_crtc(connector->encoder->crtc); + + if (!nv_crtc || !nv_crtc->set_dither) + return 0; + + return nv_crtc->set_dither(nv_crtc, nv_connector->use_dithering, + true); + } + + if (nv_encoder && nv_encoder->dcb->type == OUTPUT_TV) + return get_slave_funcs(encoder)->set_property( + encoder, connector, property, value); + + return -EINVAL; +} + +static struct drm_display_mode * +nouveau_connector_native_mode(struct drm_connector *connector) +{ + struct drm_connector_helper_funcs *helper = connector->helper_private; + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct drm_device *dev = connector->dev; + struct drm_display_mode *mode, *largest = NULL; + int high_w = 0, high_h = 0, high_v = 0; + + list_for_each_entry(mode, &nv_connector->base.probed_modes, head) { + if (helper->mode_valid(connector, mode) != MODE_OK || + (mode->flags & DRM_MODE_FLAG_INTERLACE)) + continue; + + /* Use preferred mode if there is one.. */ + if (mode->type & DRM_MODE_TYPE_PREFERRED) { + NV_DEBUG_KMS(dev, "native mode from preferred\n"); + return drm_mode_duplicate(dev, mode); + } + + /* Otherwise, take the resolution with the largest width, then + * height, then vertical refresh + */ + if (mode->hdisplay < high_w) + continue; + + if (mode->hdisplay == high_w && mode->vdisplay < high_h) + continue; + + if (mode->hdisplay == high_w && mode->vdisplay == high_h && + mode->vrefresh < high_v) + continue; + + high_w = mode->hdisplay; + high_h = mode->vdisplay; + high_v = mode->vrefresh; + largest = mode; + } + + NV_DEBUG_KMS(dev, "native mode from largest: %dx%d@%d\n", + high_w, high_h, high_v); + return largest ? drm_mode_duplicate(dev, largest) : NULL; +} + +struct moderec { + int hdisplay; + int vdisplay; +}; + +static struct moderec scaler_modes[] = { + { 1920, 1200 }, + { 1920, 1080 }, + { 1680, 1050 }, + { 1600, 1200 }, + { 1400, 1050 }, + { 1280, 1024 }, + { 1280, 960 }, + { 1152, 864 }, + { 1024, 768 }, + { 800, 600 }, + { 720, 400 }, + { 640, 480 }, + { 640, 400 }, + { 640, 350 }, + {} +}; + +static int +nouveau_connector_scaler_modes_add(struct drm_connector *connector) +{ + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct drm_display_mode *native = nv_connector->native_mode, *m; + struct drm_device *dev = connector->dev; + struct moderec *mode = &scaler_modes[0]; + int modes = 0; + + if (!native) + return 0; + + while (mode->hdisplay) { + if (mode->hdisplay <= native->hdisplay && + mode->vdisplay <= native->vdisplay) { + m = drm_cvt_mode(dev, mode->hdisplay, mode->vdisplay, + drm_mode_vrefresh(native), false, + false, false); + if (!m) + continue; + + m->type |= DRM_MODE_TYPE_DRIVER; + + drm_mode_probed_add(connector, m); + modes++; + } + + mode++; + } + + return modes; +} + +static int +nouveau_connector_get_modes(struct drm_connector *connector) +{ + struct drm_device *dev = connector->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct nouveau_encoder *nv_encoder = nv_connector->detected_encoder; + struct drm_encoder *encoder = to_drm_encoder(nv_encoder); + int ret = 0; + + /* destroy the native mode, the attached monitor could have changed. + */ + if (nv_connector->native_mode) { + drm_mode_destroy(dev, nv_connector->native_mode); + nv_connector->native_mode = NULL; + } + + if (nv_connector->edid) + ret = drm_add_edid_modes(connector, nv_connector->edid); + else + if (nv_encoder->dcb->type == OUTPUT_LVDS && + (nv_encoder->dcb->lvdsconf.use_straps_for_mode || + dev_priv->vbios.fp_no_ddc) && nouveau_bios_fp_mode(dev, NULL)) { + struct drm_display_mode mode; + + nouveau_bios_fp_mode(dev, &mode); + nv_connector->native_mode = drm_mode_duplicate(dev, &mode); + } + + /* Find the native mode if this is a digital panel, if we didn't + * find any modes through DDC previously add the native mode to + * the list of modes. + */ + if (!nv_connector->native_mode) + nv_connector->native_mode = + nouveau_connector_native_mode(connector); + if (ret == 0 && nv_connector->native_mode) { + struct drm_display_mode *mode; + + mode = drm_mode_duplicate(dev, nv_connector->native_mode); + drm_mode_probed_add(connector, mode); + ret = 1; + } + + if (nv_encoder->dcb->type == OUTPUT_TV) + ret = get_slave_funcs(encoder)->get_modes(encoder, connector); + + if (nv_connector->dcb->type == DCB_CONNECTOR_LVDS || + nv_connector->dcb->type == DCB_CONNECTOR_eDP) + ret += nouveau_connector_scaler_modes_add(connector); + + return ret; +} + +static unsigned +get_tmds_link_bandwidth(struct drm_connector *connector) +{ + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct drm_nouveau_private *dev_priv = connector->dev->dev_private; + struct dcb_entry *dcb = nv_connector->detected_encoder->dcb; + + if (dcb->location != DCB_LOC_ON_CHIP || + dev_priv->chipset >= 0x46) + return 165000; + else if (dev_priv->chipset >= 0x40) + return 155000; + else if (dev_priv->chipset >= 0x18) + return 135000; + else + return 112000; +} + +static int +nouveau_connector_mode_valid(struct drm_connector *connector, + struct drm_display_mode *mode) +{ + struct nouveau_connector *nv_connector = nouveau_connector(connector); + struct nouveau_encoder *nv_encoder = nv_connector->detected_encoder; + struct drm_encoder *encoder = to_drm_encoder(nv_encoder); + unsigned min_clock = 25000, max_clock = min_clock; + unsigned clock = mode->clock; + + switch (nv_encoder->dcb->type) { + case OUTPUT_LVDS: + if (nv_connector->native_mode && + (mode->hdisplay > nv_connector->native_mode->hdisplay || + mode->vdisplay > nv_connector->native_mode->vdisplay)) + return MODE_PANEL; + + min_clock = 0; + max_clock = 400000; + break; + case OUTPUT_TMDS: + max_clock = get_tmds_link_bandwidth(connector); + if (nouveau_duallink && nv_encoder->dcb->duallink_possible) + max_clock *= 2; + break; + case OUTPUT_ANALOG: + max_clock = nv_encoder->dcb->crtconf.maxfreq; + if (!max_clock) + max_clock = 350000; + break; + case OUTPUT_TV: + return get_slave_funcs(encoder)->mode_valid(encoder, mode); + case OUTPUT_DP: + if (nv_encoder->dp.link_bw == DP_LINK_BW_2_7) + max_clock = nv_encoder->dp.link_nr * 270000; + else + max_clock = nv_encoder->dp.link_nr * 162000; + + clock = clock * nouveau_connector_bpp(connector) / 8; + break; + default: + BUG_ON(1); + return MODE_BAD; + } + + if (clock < min_clock) + return MODE_CLOCK_LOW; + + if (clock > max_clock) + return MODE_CLOCK_HIGH; + + return MODE_OK; +} + +static struct drm_encoder * +nouveau_connector_best_encoder(struct drm_connector *connector) +{ + struct nouveau_connector *nv_connector = nouveau_connector(connector); + + if (nv_connector->detected_encoder) + return to_drm_encoder(nv_connector->detected_encoder); + + return NULL; +} + +void +nouveau_connector_set_polling(struct drm_connector *connector) +{ + struct drm_device *dev = connector->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct drm_crtc *crtc; + bool spare_crtc = false; + + list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) + spare_crtc |= !crtc->enabled; + + connector->polled = 0; + + switch (connector->connector_type) { + case DRM_MODE_CONNECTOR_VGA: + case DRM_MODE_CONNECTOR_TV: + if (dev_priv->card_type >= NV_50 || + (nv_gf4_disp_arch(dev) && spare_crtc)) + connector->polled = DRM_CONNECTOR_POLL_CONNECT; + break; + + case DRM_MODE_CONNECTOR_DVII: + case DRM_MODE_CONNECTOR_DVID: + case DRM_MODE_CONNECTOR_HDMIA: + case DRM_MODE_CONNECTOR_DisplayPort: + case DRM_MODE_CONNECTOR_eDP: + if (dev_priv->card_type >= NV_50) + connector->polled = DRM_CONNECTOR_POLL_HPD; + else if (connector->connector_type == DRM_MODE_CONNECTOR_DVID || + spare_crtc) + connector->polled = DRM_CONNECTOR_POLL_CONNECT; + break; + + default: + break; + } +} + +static const struct drm_connector_helper_funcs +nouveau_connector_helper_funcs = { + .get_modes = nouveau_connector_get_modes, + .mode_valid = nouveau_connector_mode_valid, + .best_encoder = nouveau_connector_best_encoder, +}; + +static const struct drm_connector_funcs +nouveau_connector_funcs = { + .dpms = drm_helper_connector_dpms, + .save = NULL, + .restore = NULL, + .detect = nouveau_connector_detect, + .destroy = nouveau_connector_destroy, + .fill_modes = drm_helper_probe_single_connector_modes, + .set_property = nouveau_connector_set_property, + .force = nouveau_connector_force +}; + +static const struct drm_connector_funcs +nouveau_connector_funcs_lvds = { + .dpms = drm_helper_connector_dpms, + .save = NULL, + .restore = NULL, + .detect = nouveau_connector_detect_lvds, + .destroy = nouveau_connector_destroy, + .fill_modes = drm_helper_probe_single_connector_modes, + .set_property = nouveau_connector_set_property, + .force = nouveau_connector_force +}; + +struct drm_connector * +nouveau_connector_create(struct drm_device *dev, int index) +{ + const struct drm_connector_funcs *funcs = &nouveau_connector_funcs; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_connector *nv_connector = NULL; + struct dcb_connector_table_entry *dcb = NULL; + struct drm_connector *connector; + int type, ret = 0; + + NV_DEBUG_KMS(dev, "\n"); + + if (index >= dev_priv->vbios.dcb.connector.entries) + return ERR_PTR(-EINVAL); + + dcb = &dev_priv->vbios.dcb.connector.entry[index]; + if (dcb->drm) + return dcb->drm; + + switch (dcb->type) { + case DCB_CONNECTOR_VGA: + type = DRM_MODE_CONNECTOR_VGA; + break; + case DCB_CONNECTOR_TV_0: + case DCB_CONNECTOR_TV_1: + case DCB_CONNECTOR_TV_3: + type = DRM_MODE_CONNECTOR_TV; + break; + case DCB_CONNECTOR_DVI_I: + type = DRM_MODE_CONNECTOR_DVII; + break; + case DCB_CONNECTOR_DVI_D: + type = DRM_MODE_CONNECTOR_DVID; + break; + case DCB_CONNECTOR_HDMI_0: + case DCB_CONNECTOR_HDMI_1: + type = DRM_MODE_CONNECTOR_HDMIA; + break; + case DCB_CONNECTOR_LVDS: + type = DRM_MODE_CONNECTOR_LVDS; + funcs = &nouveau_connector_funcs_lvds; + break; + case DCB_CONNECTOR_DP: + type = DRM_MODE_CONNECTOR_DisplayPort; + break; + case DCB_CONNECTOR_eDP: + type = DRM_MODE_CONNECTOR_eDP; + break; + default: + NV_ERROR(dev, "unknown connector type: 0x%02x!!\n", dcb->type); + return ERR_PTR(-EINVAL); + } + + nv_connector = kzalloc(sizeof(*nv_connector), GFP_KERNEL); + if (!nv_connector) + return ERR_PTR(-ENOMEM); + nv_connector->dcb = dcb; + connector = &nv_connector->base; + + /* defaults, will get overridden in detect() */ + connector->interlace_allowed = false; + connector->doublescan_allowed = false; + + drm_connector_init(dev, connector, funcs, type); + drm_connector_helper_add(connector, &nouveau_connector_helper_funcs); + + /* Check if we need dithering enabled */ + if (dcb->type == DCB_CONNECTOR_LVDS) { + bool dummy, is_24bit = false; + + ret = nouveau_bios_parse_lvds_table(dev, 0, &dummy, &is_24bit); + if (ret) { + NV_ERROR(dev, "Error parsing LVDS table, disabling " + "LVDS\n"); + goto fail; + } + + nv_connector->use_dithering = !is_24bit; + } + + /* Init DVI-I specific properties */ + if (dcb->type == DCB_CONNECTOR_DVI_I) { + drm_mode_create_dvi_i_properties(dev); + drm_connector_attach_property(connector, dev->mode_config.dvi_i_subconnector_property, 0); + drm_connector_attach_property(connector, dev->mode_config.dvi_i_select_subconnector_property, 0); + } + + switch (dcb->type) { + case DCB_CONNECTOR_VGA: + if (dev_priv->card_type >= NV_50) { + drm_connector_attach_property(connector, + dev->mode_config.scaling_mode_property, + nv_connector->scaling_mode); + } + /* fall-through */ + case DCB_CONNECTOR_TV_0: + case DCB_CONNECTOR_TV_1: + case DCB_CONNECTOR_TV_3: + nv_connector->scaling_mode = DRM_MODE_SCALE_NONE; + break; + default: + nv_connector->scaling_mode = DRM_MODE_SCALE_FULLSCREEN; + + drm_connector_attach_property(connector, + dev->mode_config.scaling_mode_property, + nv_connector->scaling_mode); + drm_connector_attach_property(connector, + dev->mode_config.dithering_mode_property, + nv_connector->use_dithering ? + DRM_MODE_DITHERING_ON : DRM_MODE_DITHERING_OFF); + break; + } + + nouveau_connector_set_polling(connector); + + drm_sysfs_connector_add(connector); + dcb->drm = connector; + return dcb->drm; + +fail: + drm_connector_cleanup(connector); + kfree(connector); + return ERR_PTR(ret); + +} diff --git a/driver/pscnv/nouveau_connector.h b/driver/pscnv/nouveau_connector.h new file mode 100644 index 00000000..c21ed6b1 --- /dev/null +++ b/driver/pscnv/nouveau_connector.h @@ -0,0 +1,61 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#ifndef __NOUVEAU_CONNECTOR_H__ +#define __NOUVEAU_CONNECTOR_H__ + +#include "drm_edid.h" +#include "nouveau_i2c.h" + +struct nouveau_connector { + struct drm_connector base; + + struct dcb_connector_table_entry *dcb; + + int scaling_mode; + bool use_dithering; + + struct nouveau_encoder *detected_encoder; + struct edid *edid; + struct drm_display_mode *native_mode; +}; + +static inline struct nouveau_connector *nouveau_connector( + struct drm_connector *con) +{ + return container_of(con, struct nouveau_connector, base); +} + +struct drm_connector * +nouveau_connector_create(struct drm_device *, int index); + +void +nouveau_connector_set_polling(struct drm_connector *); + +int +nouveau_connector_bpp(struct drm_connector *); + +#endif /* __NOUVEAU_CONNECTOR_H__ */ diff --git a/driver/pscnv/nouveau_crtc.h b/driver/pscnv/nouveau_crtc.h new file mode 100644 index 00000000..57cf46f9 --- /dev/null +++ b/driver/pscnv/nouveau_crtc.h @@ -0,0 +1,97 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#ifndef __NOUVEAU_CRTC_H__ +#define __NOUVEAU_CRTC_H__ + +struct nouveau_crtc { + struct drm_crtc base; + + int index; + + struct drm_display_mode *mode; + + uint32_t dpms_saved_fp_control; + uint32_t fp_users; + int saturation; + int sharpness; + int last_dpms; + + int cursor_saved_x, cursor_saved_y; + + struct { + int cpp; + bool blanked; + uint32_t offset; + uint32_t tile_flags; + } fb; + + struct { + struct pscnv_bo *nvbo; + bool visible; + uint32_t offset; + void (*set_offset)(struct nouveau_crtc *, uint32_t offset); + void (*set_pos)(struct nouveau_crtc *, int x, int y); + void (*hide)(struct nouveau_crtc *, bool update); + void (*show)(struct nouveau_crtc *, bool update); + } cursor; + + struct { + struct pscnv_bo *nvbo; + uint16_t r[256]; + uint16_t g[256]; + uint16_t b[256]; + int depth; + } lut; + + int (*set_dither)(struct nouveau_crtc *crtc, bool on, bool update); + int (*set_scale)(struct nouveau_crtc *crtc, int mode, bool update); +}; + +static inline struct nouveau_crtc *nouveau_crtc(struct drm_crtc *crtc) +{ + return container_of(crtc, struct nouveau_crtc, base); +} + +static inline struct drm_crtc *to_drm_crtc(struct nouveau_crtc *crtc) +{ + return &crtc->base; +} + +int nv50_crtc_create(struct drm_device *dev, int index); +int nv50_cursor_init(struct nouveau_crtc *); +void nv50_cursor_fini(struct nouveau_crtc *); +int nv50_crtc_cursor_set(struct drm_crtc *drm_crtc, struct drm_file *file_priv, + uint32_t buffer_handle, uint32_t width, + uint32_t height); +int nv50_crtc_cursor_move(struct drm_crtc *drm_crtc, int x, int y); + +int nv04_cursor_init(struct nouveau_crtc *); + +struct nouveau_connector * +nouveau_crtc_connector_get(struct nouveau_crtc *crtc); + +#endif /* __NOUVEAU_CRTC_H__ */ diff --git a/driver/pscnv/nouveau_debugfs.c b/driver/pscnv/nouveau_debugfs.c new file mode 100644 index 00000000..c0a66a81 --- /dev/null +++ b/driver/pscnv/nouveau_debugfs.c @@ -0,0 +1,180 @@ +/* + * Copyright (C) 2009 Red Hat + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +/* + * Authors: + * Ben Skeggs + */ + +#include + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_reg.h" + +#if 0 +static int +nouveau_debugfs_channel_info(struct seq_file *m, void *data) +{ + struct drm_info_node *node = (struct drm_info_node *) m->private; + struct nouveau_channel *chan = node->info_ent->data; + + seq_printf(m, "channel id : %d\n", chan->id); + + seq_printf(m, "cpu fifo state:\n"); + seq_printf(m, " base: 0x%08x\n", chan->pushbuf_base); + seq_printf(m, " max: 0x%08x\n", chan->dma.max << 2); + seq_printf(m, " cur: 0x%08x\n", chan->dma.cur << 2); + seq_printf(m, " put: 0x%08x\n", chan->dma.put << 2); + seq_printf(m, " free: 0x%08x\n", chan->dma.free << 2); + if (chan->dma.ib_max) { + seq_printf(m, " ib max: 0x%08x\n", chan->dma.ib_max); + seq_printf(m, " ib put: 0x%08x\n", chan->dma.ib_put); + seq_printf(m, " ib free: 0x%08x\n", chan->dma.ib_free); + } + + seq_printf(m, "gpu fifo state:\n"); + seq_printf(m, " get: 0x%08x\n", + nvchan_rd32(chan, chan->user_get)); + seq_printf(m, " put: 0x%08x\n", + nvchan_rd32(chan, chan->user_put)); + if (chan->dma.ib_max) { + seq_printf(m, " ib get: 0x%08x\n", + nvchan_rd32(chan, 0x88)); + seq_printf(m, " ib put: 0x%08x\n", + nvchan_rd32(chan, 0x8c)); + } + + seq_printf(m, "last fence : %d\n", chan->fence.sequence); + seq_printf(m, "last signalled: %d\n", chan->fence.sequence_ack); + return 0; +} + +int +nouveau_debugfs_channel_init(struct nouveau_channel *chan) +{ + struct drm_nouveau_private *dev_priv = chan->dev->dev_private; + struct drm_minor *minor = chan->dev->primary; + int ret; + + if (!dev_priv->debugfs.channel_root) { + dev_priv->debugfs.channel_root = + debugfs_create_dir("channel", minor->debugfs_root); + if (!dev_priv->debugfs.channel_root) + return -ENOENT; + } + + snprintf(chan->debugfs.name, 32, "%d", chan->id); + chan->debugfs.info.name = chan->debugfs.name; + chan->debugfs.info.show = nouveau_debugfs_channel_info; + chan->debugfs.info.driver_features = 0; + chan->debugfs.info.data = chan; + + ret = drm_debugfs_create_files(&chan->debugfs.info, 1, + dev_priv->debugfs.channel_root, + chan->dev->primary); + if (ret == 0) + chan->debugfs.active = true; + return ret; +} + +void +nouveau_debugfs_channel_fini(struct nouveau_channel *chan) +{ + struct drm_nouveau_private *dev_priv = chan->dev->dev_private; + + if (!chan->debugfs.active) + return; + + drm_debugfs_remove_files(&chan->debugfs.info, 1, chan->dev->primary); + chan->debugfs.active = false; + + if (chan == dev_priv->channel) { + debugfs_remove(dev_priv->debugfs.channel_root); + dev_priv->debugfs.channel_root = NULL; + } +} +#endif +static int +nouveau_debugfs_chipset_info(struct seq_file *m, void *data) +{ + struct drm_info_node *node = (struct drm_info_node *) m->private; + struct drm_minor *minor = node->minor; + struct drm_device *dev = minor->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t ppci_0; + + ppci_0 = nv_rd32(dev, dev_priv->chipset >= 0x40 ? 0x88000 : 0x1800); + + seq_printf(m, "PMC_BOOT_0: 0x%08x\n", nv_rd32(dev, NV03_PMC_BOOT_0)); + seq_printf(m, "PCI ID : 0x%04x:0x%04x\n", + ppci_0 & 0xffff, ppci_0 >> 16); + return 0; +} + +static int +nouveau_debugfs_memory_info(struct seq_file *m, void *data) +{ + struct drm_info_node *node = (struct drm_info_node *) m->private; + struct drm_minor *minor = node->minor; + struct drm_nouveau_private *dev_priv = minor->dev->dev_private; + + seq_printf(m, "VRAM total: %dKiB\n", (int)(dev_priv->vram_size >> 10)); + return 0; +} + +static int +nouveau_debugfs_vbios_image(struct seq_file *m, void *data) +{ + struct drm_info_node *node = (struct drm_info_node *) m->private; + struct drm_nouveau_private *dev_priv = node->minor->dev->dev_private; + int i; + + for (i = 0; i < dev_priv->vbios.length; i++) + seq_printf(m, "%c", dev_priv->vbios.data[i]); + return 0; +} + +static struct drm_info_list nouveau_debugfs_list[] = { + { "chipset", nouveau_debugfs_chipset_info, 0, NULL }, + { "memory", nouveau_debugfs_memory_info, 0, NULL }, + { "vbios.rom", nouveau_debugfs_vbios_image, 0, NULL }, +}; +#define NOUVEAU_DEBUGFS_ENTRIES ARRAY_SIZE(nouveau_debugfs_list) + +int +nouveau_debugfs_init(struct drm_minor *minor) +{ + drm_debugfs_create_files(nouveau_debugfs_list, NOUVEAU_DEBUGFS_ENTRIES, + minor->debugfs_root, minor); + return 0; +} + +void +nouveau_debugfs_takedown(struct drm_minor *minor) +{ + drm_debugfs_remove_files(nouveau_debugfs_list, NOUVEAU_DEBUGFS_ENTRIES, + minor); +} diff --git a/driver/pscnv/nouveau_display.c b/driver/pscnv/nouveau_display.c new file mode 100644 index 00000000..84f7f61f --- /dev/null +++ b/driver/pscnv/nouveau_display.c @@ -0,0 +1,106 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include "drmP.h" +#include "drm_crtc_helper.h" +#include "nouveau_drv.h" +#include "nouveau_fb.h" +#include "nouveau_fbcon.h" + +static void +nouveau_user_framebuffer_destroy(struct drm_framebuffer *drm_fb) +{ + struct nouveau_framebuffer *fb = nouveau_framebuffer(drm_fb); + + if (fb->nvbo && fb->nvbo->gem) + drm_gem_object_unreference_unlocked(fb->nvbo->gem); + + drm_framebuffer_cleanup(drm_fb); + kfree(fb); +} + +static int +nouveau_user_framebuffer_create_handle(struct drm_framebuffer *drm_fb, + struct drm_file *file_priv, + unsigned int *handle) +{ + struct nouveau_framebuffer *fb = nouveau_framebuffer(drm_fb); + + return drm_gem_handle_create(file_priv, fb->nvbo->gem, handle); +} + +static const struct drm_framebuffer_funcs nouveau_framebuffer_funcs = { + .destroy = nouveau_user_framebuffer_destroy, + .create_handle = nouveau_user_framebuffer_create_handle, +}; + +int +nouveau_framebuffer_init(struct drm_device *dev, struct nouveau_framebuffer *nouveau_fb, + struct drm_mode_fb_cmd *mode_cmd, struct pscnv_bo *nvbo) +{ + int ret; + + ret = drm_framebuffer_init(dev, &nouveau_fb->base, &nouveau_framebuffer_funcs); + if (ret) { + return ret; + } + + drm_helper_mode_fill_fb_struct(&nouveau_fb->base, mode_cmd); + nouveau_fb->nvbo = nvbo; + return 0; +} + +static struct drm_framebuffer * +nouveau_user_framebuffer_create(struct drm_device *dev, + struct drm_file *file_priv, + struct drm_mode_fb_cmd *mode_cmd) +{ + struct nouveau_framebuffer *nouveau_fb; + struct drm_gem_object *gem; + int ret; + + gem = drm_gem_object_lookup(dev, file_priv, mode_cmd->handle); + if (!gem) + return ERR_PTR(-ENOENT); + + nouveau_fb = kzalloc(sizeof(struct nouveau_framebuffer), GFP_KERNEL); + if (!nouveau_fb) + return ERR_PTR(-ENOMEM); + + ret = nouveau_framebuffer_init(dev, nouveau_fb, mode_cmd, gem->driver_private); + if (ret) { + drm_gem_object_unreference(gem); + return ERR_PTR(ret); + } + + return &nouveau_fb->base; +} + +const struct drm_mode_config_funcs nouveau_mode_config_funcs = { + .fb_create = nouveau_user_framebuffer_create, + .output_poll_changed = nouveau_fbcon_output_poll_changed, +}; + diff --git a/driver/pscnv/nouveau_dma.c b/driver/pscnv/nouveau_dma.c new file mode 100644 index 00000000..03b7625b --- /dev/null +++ b/driver/pscnv/nouveau_dma.c @@ -0,0 +1,172 @@ +/* + * Copyright (C) 2007 Ben Skeggs. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "nouveau_dma.h" + +void +nouveau_dma_pre_init(struct nouveau_channel *chan) +{ + chan->dma.max = (chan->pushbuf->size >> 2) - 2; + + chan->dma.put = 0; + chan->dma.cur = chan->dma.put; + chan->dma.free = chan->dma.max - chan->dma.cur; +} + +#if 0 +void +OUT_RINGp(struct nouveau_channel *chan, const void *data, unsigned nr_dwords) +{ + bool is_iomem; + u32 *mem = ttm_kmap_obj_virtual(&chan->pushbuf_bo->kmap, &is_iomem); + mem = &mem[chan->dma.cur]; + if (is_iomem) + memcpy_toio((void __force __iomem *)mem, data, nr_dwords * 4); + else + memcpy(mem, data, nr_dwords * 4); + chan->dma.cur += nr_dwords; +} +#endif + +/* Fetch and adjust GPU GET pointer + * + * Returns: + * value >= 0, the adjusted GET pointer + * -EINVAL if GET pointer currently outside main push buffer + * -EBUSY if timeout exceeded + */ +static inline int +READ_GET(struct nouveau_channel *chan, uint32_t *prev_get, uint32_t *timeout) +{ + uint32_t val; + + val = nv_rd32(chan->dev, chan->user_get); + + /* reset counter as long as GET is still advancing, this is + * to avoid misdetecting a GPU lockup if the GPU happens to + * just be processing an operation that takes a long time + */ + if (val != *prev_get) { + *prev_get = val; + *timeout = 0; + } + + if ((++*timeout & 0xff) == 0) { + DRM_UDELAY(1); + if (*timeout > 100000) + return -EBUSY; + } + + if (val < chan->pushbuf_base || + val > chan->pushbuf_base + (chan->dma.max << 2)) + return -EINVAL; + + return (val - chan->pushbuf_base) >> 2; +} + +int +nouveau_dma_wait(struct nouveau_channel *chan, int slots, int size) +{ + uint32_t prev_get = 0, cnt = 0; + int get; + + while (chan->dma.free < size) { + get = READ_GET(chan, &prev_get, &cnt); + if (unlikely(get == -EBUSY)) + return -EBUSY; + + /* loop until we have a usable GET pointer. the value + * we read from the GPU may be outside the main ring if + * PFIFO is processing a buffer called from the main ring, + * discard these values until something sensible is seen. + * + * the other case we discard GET is while the GPU is fetching + * from the SKIPS area, so the code below doesn't have to deal + * with some fun corner cases. + */ + if (unlikely(get == -EINVAL) || get < NOUVEAU_DMA_SKIPS) + continue; + + if (get <= chan->dma.cur) { + /* engine is fetching behind us, or is completely + * idle (GET == PUT) so we have free space up until + * the end of the push buffer + * + * we can only hit that path once per call due to + * looping back to the beginning of the push buffer, + * we'll hit the fetching-ahead-of-us path from that + * point on. + * + * the *one* exception to that rule is if we read + * GET==PUT, in which case the below conditional will + * always succeed and break us out of the wait loop. + */ + chan->dma.free = chan->dma.max - chan->dma.cur; + if (chan->dma.free >= size) + break; + + /* not enough space left at the end of the push buffer, + * instruct the GPU to jump back to the start right + * after processing the currently pending commands. + */ + OUT_RING(chan, chan->pushbuf_base | 0x20000000); + + /* wait for GET to depart from the skips area. + * prevents writing GET==PUT and causing a race + * condition that causes us to think the GPU is + * idle when it's not. + */ + do { + get = READ_GET(chan, &prev_get, &cnt); + if (unlikely(get == -EBUSY)) + return -EBUSY; + if (unlikely(get == -EINVAL)) + continue; + } while (get <= NOUVEAU_DMA_SKIPS); + WRITE_PUT(NOUVEAU_DMA_SKIPS); + + /* we're now submitting commands at the start of + * the push buffer. + */ + chan->dma.cur = + chan->dma.put = NOUVEAU_DMA_SKIPS; + } + + /* engine fetching ahead of us, we have space up until the + * current GET pointer. the "- 1" is to ensure there's + * space left to emit a jump back to the beginning of the + * push buffer if we require it. we can never get GET == PUT + * here, so this is safe. + */ + chan->dma.free = get - chan->dma.cur - 1; + } + + return 0; +} + diff --git a/driver/pscnv/nouveau_dma.h b/driver/pscnv/nouveau_dma.h new file mode 100644 index 00000000..6541f59d --- /dev/null +++ b/driver/pscnv/nouveau_dma.h @@ -0,0 +1,166 @@ +/* + * Copyright (C) 2007 Ben Skeggs. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#ifndef __NOUVEAU_DMA_H__ +#define __NOUVEAU_DMA_H__ + +#ifndef NOUVEAU_DMA_DEBUG +#define NOUVEAU_DMA_DEBUG 0 +#endif + +/* + * There's a hw race condition where you can't jump to your PUT offset, + * to avoid this we jump to offset + SKIPS and fill the difference with + * NOPs. + * + * xf86-video-nv configures the DMA fetch size to 32 bytes, and uses + * a SKIPS value of 8. Lets assume that the race condition is to do + * with writing into the fetch area, we configure a fetch size of 128 + * bytes so we need a larger SKIPS value. + */ +#define NOUVEAU_DMA_SKIPS (128 / 4) + +#if 0 +/* Hardcoded object assignments to subchannels (subchannel id). */ +enum { + NvSubM2MF = 0, + NvSubSw = 1, + NvSub2D = 2, + NvSubCtxSurf2D = 2, + NvSubGdiRect = 3, + NvSubImageBlit = 4 +}; +#endif + +/* Object handles. */ +enum { +#if 0 + NvM2MF = 0x80000001, + NvDmaFB = 0x80000002, + NvDmaTT = 0x80000003, + NvDmaVRAM = 0x80000004, + NvDmaGART = 0x80000005, + NvNotify0 = 0x80000006, + Nv2D = 0x80000007, + NvCtxSurf2D = 0x80000008, + NvRop = 0x80000009, + NvImagePatt = 0x8000000a, + NvClipRect = 0x8000000b, + NvGdiRect = 0x8000000c, + NvImageBlit = 0x8000000d, + NvSw = 0x8000000e, + NvSema = 0x8000000f, +#endif + + /* G80+ display objects */ + NvEvoVRAM = 0x01000000, + NvEvoFB16 = 0x01000001, + NvEvoFB32 = 0x01000002, + NvEvoFE = 0x01000003, +}; + +#if 0 +#define NV_MEMORY_TO_MEMORY_FORMAT 0x00000039 +#define NV_MEMORY_TO_MEMORY_FORMAT_NAME 0x00000000 +#define NV_MEMORY_TO_MEMORY_FORMAT_SET_REF 0x00000050 +#define NV_MEMORY_TO_MEMORY_FORMAT_NOP 0x00000100 +#define NV_MEMORY_TO_MEMORY_FORMAT_NOTIFY 0x00000104 +#define NV_MEMORY_TO_MEMORY_FORMAT_NOTIFY_STYLE_WRITE 0x00000000 +#define NV_MEMORY_TO_MEMORY_FORMAT_NOTIFY_STYLE_WRITE_LE_AWAKEN 0x00000001 +#define NV_MEMORY_TO_MEMORY_FORMAT_DMA_NOTIFY 0x00000180 +#define NV_MEMORY_TO_MEMORY_FORMAT_DMA_SOURCE 0x00000184 +#define NV_MEMORY_TO_MEMORY_FORMAT_OFFSET_IN 0x0000030c + +#define NV50_MEMORY_TO_MEMORY_FORMAT 0x00005039 +#define NV50_MEMORY_TO_MEMORY_FORMAT_UNK200 0x00000200 +#define NV50_MEMORY_TO_MEMORY_FORMAT_UNK21C 0x0000021c +#define NV50_MEMORY_TO_MEMORY_FORMAT_OFFSET_IN_HIGH 0x00000238 +#define NV50_MEMORY_TO_MEMORY_FORMAT_OFFSET_OUT_HIGH 0x0000023c +#endif + +#if 0 +extern void nouveau_dma_pre_init(struct nouveau_channel *); +extern int nouveau_dma_init(struct nouveau_channel *); +#endif +extern int nouveau_dma_wait(struct nouveau_channel *, int slots, int size); + +static __must_check inline int +RING_SPACE(struct nouveau_channel *chan, int size) +{ + int ret; + + ret = nouveau_dma_wait(chan, 1, size); + if (ret) + return ret; + + chan->dma.free -= size; + return 0; +} + +static inline void +OUT_RING(struct nouveau_channel *chan, int data) +{ + if (NOUVEAU_DMA_DEBUG) { + NV_INFO(chan->dev, "Ch%d/0x%08x: 0x%08x\n", + chan->id, chan->dma.cur << 2, data); + } + + nv_wv32(chan->pushbuf, 4 * chan->dma.cur++, data); +} + +extern void +OUT_RINGp(struct nouveau_channel *chan, const void *data, unsigned nr_dwords); + +static inline void +BEGIN_RING(struct nouveau_channel *chan, int subc, int mthd, int size) +{ + OUT_RING(chan, (subc << 13) | (size << 18) | mthd); +} + +#define WRITE_PUT(val) do { \ + DRM_MEMORYBARRIER(); \ + nv_rv32(chan->pushbuf, 0); \ + nv_wr32(chan->dev, chan->user_put, ((val) << 2) + chan->pushbuf_base); \ +} while (0) + +static inline void +FIRE_RING(struct nouveau_channel *chan) +{ + if (chan->dma.cur == chan->dma.put) + return; + + WRITE_PUT(chan->dma.cur); + + chan->dma.put = chan->dma.cur; +} + +static inline void +WIND_RING(struct nouveau_channel *chan) +{ + chan->dma.cur = chan->dma.put; +} + +#endif diff --git a/driver/pscnv/nouveau_dp.c b/driver/pscnv/nouveau_dp.c new file mode 100644 index 00000000..e3903a09 --- /dev/null +++ b/driver/pscnv/nouveau_dp.c @@ -0,0 +1,638 @@ +/* + * Copyright 2009 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" + +#include "nouveau_drv.h" +#include "nouveau_reg.h" +#include "nouveau_i2c.h" +#include "nouveau_connector.h" +#include "nouveau_encoder.h" + +static int +auxch_rd(struct drm_encoder *encoder, int address, uint8_t *buf, int size) +{ + struct drm_device *dev = encoder->dev; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct nouveau_i2c_chan *auxch; + int ret; + + auxch = nouveau_i2c_find(dev, nv_encoder->dcb->i2c_index); + if (!auxch) + return -ENODEV; + + ret = nouveau_dp_auxch(auxch, 9, address, buf, size); + if (ret) + return ret; + + return 0; +} + +static int +auxch_wr(struct drm_encoder *encoder, int address, uint8_t *buf, int size) +{ + struct drm_device *dev = encoder->dev; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct nouveau_i2c_chan *auxch; + int ret; + + auxch = nouveau_i2c_find(dev, nv_encoder->dcb->i2c_index); + if (!auxch) + return -ENODEV; + + ret = nouveau_dp_auxch(auxch, 8, address, buf, size); + return ret; +} + +static int +nouveau_dp_lane_count_set(struct drm_encoder *encoder, uint8_t cmd) +{ + struct drm_device *dev = encoder->dev; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + uint32_t tmp; + int or = nv_encoder->or, link = !(nv_encoder->dcb->sorconf.link & 1); + + tmp = nv_rd32(dev, NV50_SOR_DP_CTRL(or, link)); + tmp &= ~(NV50_SOR_DP_CTRL_ENHANCED_FRAME_ENABLED | + NV50_SOR_DP_CTRL_LANE_MASK); + tmp |= ((1 << (cmd & DP_LANE_COUNT_MASK)) - 1) << 16; + if (cmd & DP_LANE_COUNT_ENHANCED_FRAME_EN) + tmp |= NV50_SOR_DP_CTRL_ENHANCED_FRAME_ENABLED; + nv_wr32(dev, NV50_SOR_DP_CTRL(or, link), tmp); + + return auxch_wr(encoder, DP_LANE_COUNT_SET, &cmd, 1); +} + +static int +nouveau_dp_link_bw_set(struct drm_encoder *encoder, uint8_t cmd) +{ + struct drm_device *dev = encoder->dev; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + uint32_t tmp; + int reg = 0x614300 + (nv_encoder->or * 0x800); + + tmp = nv_rd32(dev, reg); + tmp &= 0xfff3ffff; + if (cmd == DP_LINK_BW_2_7) + tmp |= 0x00040000; + nv_wr32(dev, reg, tmp); + + return auxch_wr(encoder, DP_LINK_BW_SET, &cmd, 1); +} + +static int +nouveau_dp_link_train_set(struct drm_encoder *encoder, int pattern) +{ + struct drm_device *dev = encoder->dev; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + uint32_t tmp; + uint8_t cmd; + int or = nv_encoder->or, link = !(nv_encoder->dcb->sorconf.link & 1); + int ret; + + tmp = nv_rd32(dev, NV50_SOR_DP_CTRL(or, link)); + tmp &= ~NV50_SOR_DP_CTRL_TRAINING_PATTERN; + tmp |= (pattern << 24); + nv_wr32(dev, NV50_SOR_DP_CTRL(or, link), tmp); + + ret = auxch_rd(encoder, DP_TRAINING_PATTERN_SET, &cmd, 1); + if (ret) + return ret; + cmd &= ~DP_TRAINING_PATTERN_MASK; + cmd |= (pattern & DP_TRAINING_PATTERN_MASK); + return auxch_wr(encoder, DP_TRAINING_PATTERN_SET, &cmd, 1); +} + +static int +nouveau_dp_max_voltage_swing(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct bit_displayport_encoder_table_entry *dpse; + struct bit_displayport_encoder_table *dpe; + int i, dpe_headerlen, max_vs = 0; + + dpe = nouveau_bios_dp_table(dev, nv_encoder->dcb, &dpe_headerlen); + if (!dpe) + return false; + dpse = (void *)((char *)dpe + dpe_headerlen); + + for (i = 0; i < dpe_headerlen; i++, dpse++) { + if (dpse->vs_level > max_vs) + max_vs = dpse->vs_level; + } + + return max_vs; +} + +static int +nouveau_dp_max_pre_emphasis(struct drm_encoder *encoder, int vs) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct bit_displayport_encoder_table_entry *dpse; + struct bit_displayport_encoder_table *dpe; + int i, dpe_headerlen, max_pre = 0; + + dpe = nouveau_bios_dp_table(dev, nv_encoder->dcb, &dpe_headerlen); + if (!dpe) + return false; + dpse = (void *)((char *)dpe + dpe_headerlen); + + for (i = 0; i < dpe_headerlen; i++, dpse++) { + if (dpse->vs_level != vs) + continue; + + if (dpse->pre_level > max_pre) + max_pre = dpse->pre_level; + } + + return max_pre; +} + +static bool +nouveau_dp_link_train_adjust(struct drm_encoder *encoder, uint8_t *config) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct bit_displayport_encoder_table *dpe; + int ret, i, dpe_headerlen, vs = 0, pre = 0; + uint8_t request[2]; + + dpe = nouveau_bios_dp_table(dev, nv_encoder->dcb, &dpe_headerlen); + if (!dpe) + return false; + + ret = auxch_rd(encoder, DP_ADJUST_REQUEST_LANE0_1, request, 2); + if (ret) + return false; + + NV_DEBUG_KMS(dev, "\t\tadjust 0x%02x 0x%02x\n", request[0], request[1]); + + /* Keep all lanes at the same level.. */ + for (i = 0; i < nv_encoder->dp.link_nr; i++) { + int lane_req = (request[i >> 1] >> ((i & 1) << 2)) & 0xf; + int lane_vs = lane_req & 3; + int lane_pre = (lane_req >> 2) & 3; + + if (lane_vs > vs) + vs = lane_vs; + if (lane_pre > pre) + pre = lane_pre; + } + + if (vs >= nouveau_dp_max_voltage_swing(encoder)) { + vs = nouveau_dp_max_voltage_swing(encoder); + vs |= 4; + } + + if (pre >= nouveau_dp_max_pre_emphasis(encoder, vs & 3)) { + pre = nouveau_dp_max_pre_emphasis(encoder, vs & 3); + pre |= 4; + } + + /* Update the configuration for all lanes.. */ + for (i = 0; i < nv_encoder->dp.link_nr; i++) + config[i] = (pre << 3) | vs; + + return true; +} + +static bool +nouveau_dp_link_train_commit(struct drm_encoder *encoder, uint8_t *config) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct bit_displayport_encoder_table_entry *dpse; + struct bit_displayport_encoder_table *dpe; + int or = nv_encoder->or, link = !(nv_encoder->dcb->sorconf.link & 1); + int dpe_headerlen, ret, i; + + NV_DEBUG_KMS(dev, "\t\tconfig 0x%02x 0x%02x 0x%02x 0x%02x\n", + config[0], config[1], config[2], config[3]); + + dpe = nouveau_bios_dp_table(dev, nv_encoder->dcb, &dpe_headerlen); + if (!dpe) + return false; + dpse = (void *)((char *)dpe + dpe_headerlen); + + for (i = 0; i < dpe->record_nr; i++, dpse++) { + if (dpse->vs_level == (config[0] & 3) && + dpse->pre_level == ((config[0] >> 3) & 3)) + break; + } + BUG_ON(i == dpe->record_nr); + + for (i = 0; i < nv_encoder->dp.link_nr; i++) { + const int shift[4] = { 16, 8, 0, 24 }; + uint32_t mask = 0xff << shift[i]; + uint32_t reg0, reg1, reg2; + + reg0 = nv_rd32(dev, NV50_SOR_DP_UNK118(or, link)) & ~mask; + reg0 |= (dpse->reg0 << shift[i]); + reg1 = nv_rd32(dev, NV50_SOR_DP_UNK120(or, link)) & ~mask; + reg1 |= (dpse->reg1 << shift[i]); + reg2 = nv_rd32(dev, NV50_SOR_DP_UNK130(or, link)) & 0xffff00ff; + reg2 |= (dpse->reg2 << 8); + nv_wr32(dev, NV50_SOR_DP_UNK118(or, link), reg0); + nv_wr32(dev, NV50_SOR_DP_UNK120(or, link), reg1); + nv_wr32(dev, NV50_SOR_DP_UNK130(or, link), reg2); + } + + ret = auxch_wr(encoder, DP_TRAINING_LANE0_SET, config, 4); + if (ret) + return false; + + return true; +} + +bool +nouveau_dp_link_train(struct drm_encoder *encoder) +{ + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_gpio_engine *pgpio = &dev_priv->engine.gpio; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct nouveau_connector *nv_connector; + struct bit_displayport_encoder_table *dpe; + int dpe_headerlen; + uint8_t config[4], status[3]; + bool cr_done, cr_max_vs, eq_done; + int ret = 0, i, tries, voltage; + + NV_DEBUG_KMS(dev, "link training!!\n"); + + nv_connector = nouveau_encoder_connector_get(nv_encoder); + if (!nv_connector) + return false; + + dpe = nouveau_bios_dp_table(dev, nv_encoder->dcb, &dpe_headerlen); + if (!dpe) { + NV_ERROR(dev, "SOR-%d: no DP encoder table!\n", nv_encoder->or); + return false; + } + + /* disable hotplug detect, this flips around on some panels during + * link training. + */ + pgpio->irq_enable(dev, nv_connector->dcb->gpio_tag, false); + + if (dpe->script0) { + NV_DEBUG_KMS(dev, "SOR-%d: running DP script 0\n", nv_encoder->or); + nouveau_bios_run_init_table(dev, le16_to_cpu(dpe->script0), + nv_encoder->dcb); + } + +train: + cr_done = eq_done = false; + + /* set link configuration */ + NV_DEBUG_KMS(dev, "\tbegin train: bw %d, lanes %d\n", + nv_encoder->dp.link_bw, nv_encoder->dp.link_nr); + + ret = nouveau_dp_link_bw_set(encoder, nv_encoder->dp.link_bw); + if (ret) + return false; + + config[0] = nv_encoder->dp.link_nr; + if (nv_encoder->dp.dpcd_version >= 0x11 && + nv_encoder->dp.enhanced_frame) + config[0] |= DP_LANE_COUNT_ENHANCED_FRAME_EN; + + ret = nouveau_dp_lane_count_set(encoder, config[0]); + if (ret) + return false; + + /* clock recovery */ + NV_DEBUG_KMS(dev, "\tbegin cr\n"); + ret = nouveau_dp_link_train_set(encoder, DP_TRAINING_PATTERN_1); + if (ret) + goto stop; + + tries = 0; + voltage = -1; + memset(config, 0x00, sizeof(config)); + for (;;) { + if (!nouveau_dp_link_train_commit(encoder, config)) + break; + + udelay(100); + + ret = auxch_rd(encoder, DP_LANE0_1_STATUS, status, 2); + if (ret) + break; + NV_DEBUG_KMS(dev, "\t\tstatus: 0x%02x 0x%02x\n", + status[0], status[1]); + + cr_done = true; + cr_max_vs = false; + for (i = 0; i < nv_encoder->dp.link_nr; i++) { + int lane = (status[i >> 1] >> ((i & 1) * 4)) & 0xf; + + if (!(lane & DP_LANE_CR_DONE)) { + cr_done = false; + if (config[i] & DP_TRAIN_MAX_PRE_EMPHASIS_REACHED) + cr_max_vs = true; + break; + } + } + + if ((config[0] & DP_TRAIN_VOLTAGE_SWING_MASK) != voltage) { + voltage = config[0] & DP_TRAIN_VOLTAGE_SWING_MASK; + tries = 0; + } + + if (cr_done || cr_max_vs || (++tries == 5)) + break; + + if (!nouveau_dp_link_train_adjust(encoder, config)) + break; + } + + if (!cr_done) + goto stop; + + /* channel equalisation */ + NV_DEBUG_KMS(dev, "\tbegin eq\n"); + ret = nouveau_dp_link_train_set(encoder, DP_TRAINING_PATTERN_2); + if (ret) + goto stop; + + for (tries = 0; tries <= 5; tries++) { + udelay(400); + + ret = auxch_rd(encoder, DP_LANE0_1_STATUS, status, 3); + if (ret) + break; + NV_DEBUG_KMS(dev, "\t\tstatus: 0x%02x 0x%02x\n", + status[0], status[1]); + + eq_done = true; + if (!(status[2] & DP_INTERLANE_ALIGN_DONE)) + eq_done = false; + + for (i = 0; eq_done && i < nv_encoder->dp.link_nr; i++) { + int lane = (status[i >> 1] >> ((i & 1) * 4)) & 0xf; + + if (!(lane & DP_LANE_CR_DONE)) { + cr_done = false; + break; + } + + if (!(lane & DP_LANE_CHANNEL_EQ_DONE) || + !(lane & DP_LANE_SYMBOL_LOCKED)) { + eq_done = false; + break; + } + } + + if (eq_done || !cr_done) + break; + + if (!nouveau_dp_link_train_adjust(encoder, config) || + !nouveau_dp_link_train_commit(encoder, config)) + break; + } + +stop: + /* end link training */ + ret = nouveau_dp_link_train_set(encoder, DP_TRAINING_PATTERN_DISABLE); + if (ret) + return false; + + /* retry at a lower setting, if possible */ + if (!ret && !(eq_done && cr_done)) { + NV_DEBUG_KMS(dev, "\twe failed\n"); + if (nv_encoder->dp.link_bw != DP_LINK_BW_1_62) { + NV_DEBUG_KMS(dev, "retry link training at low rate\n"); + nv_encoder->dp.link_bw = DP_LINK_BW_1_62; + goto train; + } + } + + if (dpe->script1) { + NV_DEBUG_KMS(dev, "SOR-%d: running DP script 1\n", nv_encoder->or); + nouveau_bios_run_init_table(dev, le16_to_cpu(dpe->script1), + nv_encoder->dcb); + } + + /* re-enable hotplug detect */ + pgpio->irq_enable(dev, nv_connector->dcb->gpio_tag, true); + + return eq_done; +} + +bool +nouveau_dp_detect(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + uint8_t dpcd[4]; + int ret; + + ret = auxch_rd(encoder, 0x0000, dpcd, 4); + if (ret) + return false; + + NV_DEBUG_KMS(dev, "encoder: link_bw %d, link_nr %d\n" + "display: link_bw %d, link_nr %d version 0x%02x\n", + nv_encoder->dcb->dpconf.link_bw, + nv_encoder->dcb->dpconf.link_nr, + dpcd[1], dpcd[2] & 0x0f, dpcd[0]); + + nv_encoder->dp.dpcd_version = dpcd[0]; + + nv_encoder->dp.link_bw = dpcd[1]; + if (nv_encoder->dp.link_bw != DP_LINK_BW_1_62 && + !nv_encoder->dcb->dpconf.link_bw) + nv_encoder->dp.link_bw = DP_LINK_BW_1_62; + + nv_encoder->dp.link_nr = dpcd[2] & DP_MAX_LANE_COUNT_MASK; + if (nv_encoder->dp.link_nr > nv_encoder->dcb->dpconf.link_nr) + nv_encoder->dp.link_nr = nv_encoder->dcb->dpconf.link_nr; + + nv_encoder->dp.enhanced_frame = (dpcd[2] & DP_ENHANCED_FRAME_CAP); + + return true; +} + +int +nouveau_dp_auxch(struct nouveau_i2c_chan *auxch, int cmd, int addr, + uint8_t *data, int data_nr) +{ + struct drm_device *dev = auxch->dev; + uint32_t tmp, ctrl, stat = 0, data32[4] = {}; + int ret = 0, i, index = auxch->rd; + + NV_DEBUG_KMS(dev, "ch %d cmd %d addr 0x%x len %d\n", index, cmd, addr, data_nr); + + tmp = nv_rd32(dev, NV50_AUXCH_CTRL(auxch->rd)); + nv_wr32(dev, NV50_AUXCH_CTRL(auxch->rd), tmp | 0x00100000); + tmp = nv_rd32(dev, NV50_AUXCH_CTRL(auxch->rd)); + if (!(tmp & 0x01000000)) { + NV_ERROR(dev, "expected bit 24 == 1, got 0x%08x\n", tmp); + ret = -EIO; + goto out; + } + + for (i = 0; i < 3; i++) { + tmp = nv_rd32(dev, NV50_AUXCH_STAT(auxch->rd)); + if (tmp & NV50_AUXCH_STAT_STATE_READY) + break; + udelay(100); + } + + if (i == 3) { + ret = -EBUSY; + goto out; + } + + if (!(cmd & 1)) { + memcpy(data32, data, data_nr); + for (i = 0; i < 4; i++) { + NV_DEBUG_KMS(dev, "wr %d: 0x%08x\n", i, data32[i]); + nv_wr32(dev, NV50_AUXCH_DATA_OUT(index, i), data32[i]); + } + } + + nv_wr32(dev, NV50_AUXCH_ADDR(index), addr); + ctrl = nv_rd32(dev, NV50_AUXCH_CTRL(index)); + ctrl &= ~(NV50_AUXCH_CTRL_CMD | NV50_AUXCH_CTRL_LEN); + ctrl |= (cmd << NV50_AUXCH_CTRL_CMD_SHIFT); + ctrl |= ((data_nr - 1) << NV50_AUXCH_CTRL_LEN_SHIFT); + + for (i = 0; i < 16; i++) { + nv_wr32(dev, NV50_AUXCH_CTRL(index), ctrl | 0x80000000); + nv_wr32(dev, NV50_AUXCH_CTRL(index), ctrl); + nv_wr32(dev, NV50_AUXCH_CTRL(index), ctrl | 0x00010000); + if (!nv_wait(dev, NV50_AUXCH_CTRL(index), + 0x00010000, 0x00000000)) { + NV_ERROR(dev, "expected bit 16 == 0, got 0x%08x\n", + nv_rd32(dev, NV50_AUXCH_CTRL(index))); + ret = -EBUSY; + goto out; + } + + udelay(400); + + stat = nv_rd32(dev, NV50_AUXCH_STAT(index)); + if ((stat & NV50_AUXCH_STAT_REPLY_AUX) != + NV50_AUXCH_STAT_REPLY_AUX_DEFER) + break; + } + + if (i == 16) { + NV_ERROR(dev, "auxch DEFER too many times, bailing\n"); + ret = -EREMOTEIO; + goto out; + } + + if (cmd & 1) { + if ((stat & NV50_AUXCH_STAT_COUNT) != data_nr) { + ret = -EREMOTEIO; + goto out; + } + + for (i = 0; i < 4; i++) { + data32[i] = nv_rd32(dev, NV50_AUXCH_DATA_IN(index, i)); + NV_DEBUG_KMS(dev, "rd %d: 0x%08x\n", i, data32[i]); + } + memcpy(data, data32, data_nr); + } + +out: + tmp = nv_rd32(dev, NV50_AUXCH_CTRL(auxch->rd)); + nv_wr32(dev, NV50_AUXCH_CTRL(auxch->rd), tmp & ~0x00100000); + tmp = nv_rd32(dev, NV50_AUXCH_CTRL(auxch->rd)); + if (tmp & 0x01000000) { + NV_ERROR(dev, "expected bit 24 == 0, got 0x%08x\n", tmp); + ret = -EIO; + } + + udelay(400); + + return ret ? ret : (stat & NV50_AUXCH_STAT_REPLY); +} + +static int +nouveau_dp_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num) +{ + struct nouveau_i2c_chan *auxch = (struct nouveau_i2c_chan *)adap; + struct drm_device *dev = auxch->dev; + struct i2c_msg *msg = msgs; + int ret, mcnt = num; + + while (mcnt--) { + u8 remaining = msg->len; + u8 *ptr = msg->buf; + + while (remaining) { + u8 cnt = (remaining > 16) ? 16 : remaining; + u8 cmd; + + if (msg->flags & I2C_M_RD) + cmd = AUX_I2C_READ; + else + cmd = AUX_I2C_WRITE; + + if (mcnt || remaining > 16) + cmd |= AUX_I2C_MOT; + + ret = nouveau_dp_auxch(auxch, cmd, msg->addr, ptr, cnt); + if (ret < 0) + return ret; + + switch (ret & NV50_AUXCH_STAT_REPLY_I2C) { + case NV50_AUXCH_STAT_REPLY_I2C_ACK: + break; + case NV50_AUXCH_STAT_REPLY_I2C_NACK: + return -EREMOTEIO; + case NV50_AUXCH_STAT_REPLY_I2C_DEFER: + udelay(100); + continue; + default: + NV_ERROR(dev, "bad auxch reply: 0x%08x\n", ret); + return -EREMOTEIO; + } + + ptr += cnt; + remaining -= cnt; + } + + msg++; + } + + return num; +} + +static u32 +nouveau_dp_i2c_func(struct i2c_adapter *adap) +{ + return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL; +} + +const struct i2c_algorithm nouveau_dp_i2c_algo = { + .master_xfer = nouveau_dp_i2c_xfer, + .functionality = nouveau_dp_i2c_func +}; diff --git a/driver/pscnv/nouveau_drv.c b/driver/pscnv/nouveau_drv.c new file mode 100644 index 00000000..f1447fd7 --- /dev/null +++ b/driver/pscnv/nouveau_drv.c @@ -0,0 +1,533 @@ +/* + * Copyright 2005 Stephane Marchesin. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include +#ifdef __linux__ +#include +#endif + +#include "drmP.h" +#include "drm.h" +#include "drm_crtc_helper.h" +#include "nouveau_drv.h" +#include "nouveau_pm.h" +#include "pscnv_gem.h" +#include "pscnv_vm.h" +#if 0 +#include "nouveau_hw.h" +#include "nouveau_fb.h" +#include "nouveau_fbcon.h" +#include "nv50_display.h" +#endif + +#include "drm_pciids.h" +#include "pscnv_kapi.h" + +MODULE_PARM_DESC(agpmode, "AGP mode (0 to disable AGP)"); +int nouveau_agpmode = -1; +module_param_named(agpmode, nouveau_agpmode, int, 0400); + +MODULE_PARM_DESC(modeset, "Enable kernel modesetting"); +static int nouveau_modeset = 1; /* kms */ +module_param_named(modeset, nouveau_modeset, int, 0400); + +MODULE_PARM_DESC(vbios, "Override default VBIOS location"); +char *nouveau_vbios; +module_param_named(vbios, nouveau_vbios, charp, 0400); + +MODULE_PARM_DESC(duallink, "Allow dual-link TMDS (>=GeForce 8)"); +int nouveau_duallink = 1; +module_param_named(duallink, nouveau_duallink, int, 0400); + +MODULE_PARM_DESC(uscript_lvds, "LVDS output script table ID (>=GeForce 8)"); +int nouveau_uscript_lvds = -1; +module_param_named(uscript_lvds, nouveau_uscript_lvds, int, 0400); + +MODULE_PARM_DESC(uscript_tmds, "TMDS output script table ID (>=GeForce 8)"); +int nouveau_uscript_tmds = -1; +module_param_named(uscript_tmds, nouveau_uscript_tmds, int, 0400); + +MODULE_PARM_DESC(ignorelid, "Ignore ACPI lid status"); +int nouveau_ignorelid = 0; +module_param_named(ignorelid, nouveau_ignorelid, int, 0400); + +MODULE_PARM_DESC(noaccel, "Disable all acceleration"); +int nouveau_noaccel = 0; +module_param_named(noaccel, nouveau_noaccel, int, 0400); + +MODULE_PARM_DESC(nofbaccel, "Disable fbcon acceleration"); +int nouveau_nofbaccel = 0; +module_param_named(nofbaccel, nouveau_nofbaccel, int, 0400); + +MODULE_PARM_DESC(force_post, "Force POST"); +int nouveau_force_post = 0; +module_param_named(force_post, nouveau_force_post, int, 0400); + +MODULE_PARM_DESC(override_conntype, "Ignore DCB connector type"); +int nouveau_override_conntype = 0; +module_param_named(override_conntype, nouveau_override_conntype, int, 0400); + +MODULE_PARM_DESC(tv_disable, "Disable TV-out detection\n"); +int nouveau_tv_disable = 0; +module_param_named(tv_disable, nouveau_tv_disable, int, 0400); + +MODULE_PARM_DESC(tv_norm, "Default TV norm.\n" + "\t\tSupported: PAL, PAL-M, PAL-N, PAL-Nc, NTSC-M, NTSC-J,\n" + "\t\t\thd480i, hd480p, hd576i, hd576p, hd720p, hd1080i.\n" + "\t\tDefault: PAL\n" + "\t\t*NOTE* Ignored for cards with external TV encoders."); +char *nouveau_tv_norm; +module_param_named(tv_norm, nouveau_tv_norm, charp, 0400); + +MODULE_PARM_DESC(reg_debug, "Register access debug bitmask:\n" + "\t\t0x1 mc, 0x2 video, 0x4 fb, 0x8 extdev,\n" + "\t\t0x10 crtc, 0x20 ramdac, 0x40 vgacrtc, 0x80 rmvio,\n" + "\t\t0x100 vgaattr, 0x200 EVO (G80+). "); +int nouveau_reg_debug; +module_param_named(reg_debug, nouveau_reg_debug, int, 0600); + +MODULE_PARM_DESC(perflvl, "Performance level (default: boot)\n"); +char *nouveau_perflvl; +module_param_named(perflvl, nouveau_perflvl, charp, 0400); + +MODULE_PARM_DESC(perflvl_wr, "Allow perflvl changes (warning: dangerous!)\n"); +int nouveau_perflvl_wr; +module_param_named(perflvl_wr, nouveau_perflvl_wr, int, 0400); + +MODULE_PARM_DESC(mm_debug, "mm debug level: 0-2."); +int pscnv_mm_debug = 0; +module_param_named(mm_debug, pscnv_mm_debug, int, 0400); + +MODULE_PARM_DESC(mem_debug, "memory debug level: 0-1."); +int pscnv_mem_debug = 0; +module_param_named(mem_debug, pscnv_mem_debug, int, 0400); + +MODULE_PARM_DESC(vm_debug, "VM debug level: 0-2."); +int pscnv_vm_debug = 0; +module_param_named(vm_debug, pscnv_vm_debug, int, 0400); + +MODULE_PARM_DESC(ramht_debug, "RAMHT debug level: 0-2."); +int pscnv_ramht_debug = 0; +module_param_named(ramht_debug, pscnv_ramht_debug, int, 0400); + +MODULE_PARM_DESC(gem_debug, "GEM debug level: 0-1."); +int pscnv_gem_debug = 0; +module_param_named(gem_debug, pscnv_gem_debug, int, 0400); + +int nouveau_fbpercrtc; +#if 0 +module_param_named(fbpercrtc, nouveau_fbpercrtc, int, 0400); +#endif + +static struct pci_device_id pciidlist[] = { + { + PCI_DEVICE(PCI_VENDOR_ID_NVIDIA, PCI_ANY_ID), + .class = PCI_BASE_CLASS_DISPLAY << 16, + .class_mask = 0xff << 16, + }, + { + PCI_DEVICE(PCI_VENDOR_ID_NVIDIA_SGS, PCI_ANY_ID), + .class = PCI_BASE_CLASS_DISPLAY << 16, + .class_mask = 0xff << 16, + }, + {} +}; + +MODULE_DEVICE_TABLE(pci, pciidlist); + +static struct drm_driver driver; + +static int __devinit +nouveau_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent) +{ +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36) + return drm_get_pci_dev(pdev, ent, &driver); +#else + return drm_get_dev(pdev, ent, &driver); +#endif +} + +static void +nouveau_pci_remove(struct pci_dev *pdev) +{ + struct drm_device *dev = pci_get_drvdata(pdev); + + drm_put_dev(dev); +} + +int +nouveau_pci_suspend(struct pci_dev *pdev, pm_message_t pm_state) +{ + return -ENODEV; +#if 0 + struct drm_device *dev = pci_get_drvdata(pdev); + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_instmem_engine *pinstmem = &dev_priv->engine.instmem; + struct nouveau_pgraph_engine *pgraph = &dev_priv->engine.graph; + struct nouveau_fifo_engine *pfifo = &dev_priv->engine.fifo; + struct nouveau_channel *chan; + struct drm_crtc *crtc; + int ret, i; + + if (!drm_core_check_feature(dev, DRIVER_MODESET)) + return -ENODEV; + + if (pm_state.event == PM_EVENT_PRETHAW) + return 0; + + NV_INFO(dev, "Disabling fbcon acceleration...\n"); + nouveau_fbcon_save_disable_accel(dev); + + NV_INFO(dev, "Unpinning framebuffer(s)...\n"); + list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { + struct nouveau_framebuffer *nouveau_fb; + + nouveau_fb = nouveau_framebuffer(crtc->fb); + if (!nouveau_fb || !nouveau_fb->nvbo) + continue; + + nouveau_bo_unpin(nouveau_fb->nvbo); + } + + list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + + nouveau_bo_unmap(nv_crtc->cursor.nvbo); + nouveau_bo_unpin(nv_crtc->cursor.nvbo); + } + + NV_INFO(dev, "Evicting buffers...\n"); + ttm_bo_evict_mm(&dev_priv->ttm.bdev, TTM_PL_VRAM); + + NV_INFO(dev, "Idling channels...\n"); + for (i = 0; i < pfifo->channels; i++) { + struct nouveau_fence *fence = NULL; + + chan = dev_priv->channels.ptr[i]; + if (!chan || !chan->pushbuf_bo) + continue; + + ret = nouveau_fence_new(chan, &fence, true); + if (ret == 0) { + ret = nouveau_fence_wait(fence, NULL, false, false); + nouveau_fence_unref((void *)&fence); + } + + if (ret) { + NV_ERROR(dev, "Failed to idle channel %d for suspend\n", + chan->id); + } + } + + pgraph->fifo_access(dev, false); + nouveau_wait_for_idle(dev); + pfifo->reassign(dev, false); + pfifo->disable(dev); + pfifo->unload_context(dev); + pgraph->unload_context(dev); + + NV_INFO(dev, "Suspending GPU objects...\n"); + ret = nouveau_gpuobj_suspend(dev); + if (ret) { + NV_ERROR(dev, "... failed: %d\n", ret); + goto out_abort; + } + + ret = pinstmem->suspend(dev); + if (ret) { + NV_ERROR(dev, "... failed: %d\n", ret); + nouveau_gpuobj_suspend_cleanup(dev); + goto out_abort; + } + + NV_INFO(dev, "And we're gone!\n"); + pci_save_state(pdev); + if (pm_state.event == PM_EVENT_SUSPEND) { + pci_disable_device(pdev); + pci_set_power_state(pdev, PCI_D3hot); + } + + acquire_console_sem(); + nouveau_fbcon_set_suspend(dev, 1); + release_console_sem(); + nouveau_fbcon_restore_accel(dev); + return 0; + +out_abort: + NV_INFO(dev, "Re-enabling acceleration..\n"); + pfifo->enable(dev); + pfifo->reassign(dev, true); + pgraph->fifo_access(dev, true); + return ret; +#endif +} + +int +nouveau_pci_resume(struct pci_dev *pdev) +{ + return -ENODEV; +#if 0 + struct drm_device *dev = pci_get_drvdata(pdev); + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_engine *engine = &dev_priv->engine; + struct drm_crtc *crtc; + int ret, i; + + if (!drm_core_check_feature(dev, DRIVER_MODESET)) + return -ENODEV; + + nouveau_fbcon_save_disable_accel(dev); + + NV_INFO(dev, "We're back, enabling device...\n"); + pci_set_power_state(pdev, PCI_D0); + pci_restore_state(pdev); + if (pci_enable_device(pdev)) + return -1; + pci_set_master(dev->pdev); + + NV_INFO(dev, "POSTing device...\n"); + ret = nouveau_run_vbios_init(dev); + if (ret) + return ret; + + nouveau_pm_resume(dev); + + if (dev_priv->gart_info.type == NOUVEAU_GART_AGP) { + ret = nouveau_mem_init_agp(dev); + if (ret) { + NV_ERROR(dev, "error reinitialising AGP: %d\n", ret); + return ret; + } + } + + NV_INFO(dev, "Reinitialising engines...\n"); + engine->instmem.resume(dev); + engine->mc.init(dev); + engine->timer.init(dev); + engine->fb.init(dev); + engine->graph.init(dev); + engine->fifo.init(dev); + + NV_INFO(dev, "Restoring GPU objects...\n"); + nouveau_gpuobj_resume(dev); + + nouveau_irq_postinstall(dev); + + /* Re-write SKIPS, they'll have been lost over the suspend */ + if (nouveau_vram_pushbuf) { + struct nouveau_channel *chan; + int j; + + for (i = 0; i < dev_priv->engine.fifo.channels; i++) { + chan = dev_priv->channels.ptr[i]; + if (!chan || !chan->pushbuf_bo) + continue; + + for (j = 0; j < NOUVEAU_DMA_SKIPS; j++) + nouveau_bo_wr32(chan->pushbuf_bo, i, 0); + } + } + + NV_INFO(dev, "Restoring mode...\n"); + list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { + struct nouveau_framebuffer *nouveau_fb; + + nouveau_fb = nouveau_framebuffer(crtc->fb); + if (!nouveau_fb || !nouveau_fb->nvbo) + continue; + + nouveau_bo_pin(nouveau_fb->nvbo, TTM_PL_FLAG_VRAM); + } + + list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + int ret; + + ret = nouveau_bo_pin(nv_crtc->cursor.nvbo, TTM_PL_FLAG_VRAM); + if (!ret) + ret = nouveau_bo_map(nv_crtc->cursor.nvbo); + if (ret) + NV_ERROR(dev, "Could not pin/map cursor.\n"); + } + + if (dev_priv->card_type < NV_50) { + nv04_display_restore(dev); + NVLockVgaCrtcs(dev, false); + } else + nv50_display_init(dev); + + list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + + nv_crtc->cursor.set_offset(nv_crtc, + nv_crtc->cursor.nvbo->bo.offset - + dev_priv->vm_vram_base); + + nv_crtc->cursor.set_pos(nv_crtc, nv_crtc->cursor_saved_x, + nv_crtc->cursor_saved_y); + } + + /* Force CLUT to get re-loaded during modeset */ + list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + + nv_crtc->lut.depth = 0; + } + + acquire_console_sem(); + nouveau_fbcon_set_suspend(dev, 0); + release_console_sem(); + + nouveau_fbcon_zfill_all(dev); + + drm_helper_resume_force_mode(dev); + + nouveau_fbcon_restore_accel(dev); + return 0; +#endif +} + +static struct drm_driver driver = { + .driver_features = + DRIVER_USE_AGP | DRIVER_PCI_DMA | DRIVER_SG | + DRIVER_HAVE_IRQ | DRIVER_IRQ_SHARED | DRIVER_GEM, + .load = nouveau_load, + .firstopen = nouveau_firstopen, + .lastclose = nouveau_lastclose, + .unload = nouveau_unload, + .preclose = nouveau_preclose, +#if defined(CONFIG_DRM_NOUVEAU_DEBUG) + .debugfs_init = nouveau_debugfs_init, + .debugfs_cleanup = nouveau_debugfs_takedown, +#endif + .irq_preinstall = nouveau_irq_preinstall, + .irq_postinstall = nouveau_irq_postinstall, + .irq_uninstall = nouveau_irq_uninstall, + .irq_handler = nouveau_irq_handler, + .reclaim_buffers = drm_core_reclaim_buffers, +#ifdef PSCNV_KAPI_MAP_OFS + .get_map_ofs = drm_core_get_map_ofs, + .get_reg_ofs = drm_core_get_reg_ofs, +#endif + .ioctls = nouveau_ioctls, + .fops = { + .owner = THIS_MODULE, + .open = drm_open, + .release = drm_release, + .unlocked_ioctl = drm_ioctl, + .mmap = pscnv_mmap, + .poll = drm_poll, + .fasync = drm_fasync, +#if defined(CONFIG_COMPAT) + .compat_ioctl = nouveau_compat_ioctl, +#endif + }, + +#ifdef PSCNV_KAPI_PCI_DRIVER + .pci_driver = { + .name = DRIVER_NAME, + .id_table = pciidlist, + .probe = nouveau_pci_probe, + .remove = nouveau_pci_remove, + .suspend = nouveau_pci_suspend, + .resume = nouveau_pci_resume + }, +#endif + + .gem_free_object = pscnv_gem_free_object, + //.gem_close_object = pscnv_gem_object_close, + + .name = DRIVER_NAME, + .desc = DRIVER_DESC, +#ifdef GIT_REVISION + .date = GIT_REVISION, +#else + .date = DRIVER_DATE, +#endif + .major = DRIVER_MAJOR, + .minor = DRIVER_MINOR, + .patchlevel = DRIVER_PATCHLEVEL, +}; + +static struct pci_driver nouveau_pci_driver = { + .name = DRIVER_NAME, + .id_table = pciidlist, + .probe = nouveau_pci_probe, + .remove = nouveau_pci_remove, + .suspend = nouveau_pci_suspend, + .resume = nouveau_pci_resume +}; + +#include "gdev_drv.h" + +static int __init nouveau_init(void) +{ + gdev_major_init(&nouveau_pci_driver); + + driver.num_ioctls = nouveau_max_ioctl; + + if (nouveau_modeset == -1) { +#ifdef CONFIG_VGA_CONSOLE + if (vgacon_text_force()) + nouveau_modeset = 0; + else +#endif + nouveau_modeset = 1; + } + + if (nouveau_modeset == 1) { + driver.driver_features |= DRIVER_MODESET; +#if defined(CONFIG_FRAMEBUFFER_CONSOLE_MODULE) + request_module("fbcon"); +#elif !defined(CONFIG_FRAMEBUFFER_CONSOLE) + printk(KERN_INFO "CONFIG_FRAMEBUFFER_CONSOLE was not enabled. You won't get any console output.\n"); +#endif + nouveau_register_dsm_handler(); + } + +#ifdef PSCNV_KAPI_PCI_DRIVER + return drm_init(&driver); +#else + return drm_pci_init(&driver, &nouveau_pci_driver); +#endif +} + +static void __exit nouveau_exit(void) +{ +#ifdef PSCNV_KAPI_PCI_DRIVER + drm_exit(&driver); +#else + drm_pci_exit(&driver, &nouveau_pci_driver); +#endif + nouveau_unregister_dsm_handler(); + + gdev_major_exit(); +} + +module_init(nouveau_init); +module_exit(nouveau_exit); + +MODULE_AUTHOR(DRIVER_AUTHOR); +MODULE_DESCRIPTION(DRIVER_DESC); +MODULE_LICENSE("GPL and additional rights"); diff --git a/driver/pscnv/nouveau_drv.h b/driver/pscnv/nouveau_drv.h new file mode 100644 index 00000000..aba5a4ab --- /dev/null +++ b/driver/pscnv/nouveau_drv.h @@ -0,0 +1,1234 @@ +/* + * Copyright 2005 Stephane Marchesin. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __NOUVEAU_DRV_H__ +#define __NOUVEAU_DRV_H__ + +#define DRIVER_AUTHOR "Stephane Marchesin" +#define DRIVER_EMAIL "dri-devel@lists.sourceforge.net" + +#define DRIVER_NAME "pscnv" +#define DRIVER_DESC "nVidia NV50" +#define DRIVER_DATE "20090420" + +#define DRIVER_MAJOR 0 +#define DRIVER_MINOR 0 +#define DRIVER_PATCHLEVEL 16 + +#define DRM_FILE_PAGE_OFFSET (0x100000000ULL >> PAGE_SHIFT) + +#include "nouveau_bios.h" +#include "pscnv_mem.h" +#include "pscnv_ramht.h" +#include "pscnv_engine.h" +struct nouveau_grctx; + +typedef void (*nouveau_irqhandler_t) (struct drm_device *dev, int irq); + +#define MAX_NUM_DCB_ENTRIES 16 + +#define NOUVEAU_MAX_CHANNEL_NR 128 +#define NOUVEAU_MAX_TILE_NR 15 + +#define NV50_VM_MAX_VRAM (2*1024*1024*1024ULL) +#define NV50_VM_BLOCK (512*1024*1024ULL) +#define NV50_VM_VRAM_NR (NV50_VM_MAX_VRAM / NV50_VM_BLOCK) + +#if 0 /* for pre-NV50 */ +struct nouveau_tile_reg { + struct nouveau_fence *fence; + uint32_t addr; + uint32_t size; + bool used; +}; +#endif + +enum nouveau_flags { + NV_NFORCE = 0x10000000, + NV_NFORCE2 = 0x20000000 +}; + +struct pscnv_bo; + +struct nouveau_channel { + struct drm_device *dev; + int id; + + /* mapping of the regs controling the fifo */ + uint32_t user_get; + uint32_t user_put; + + /* Fencing */ + struct { + /* lock protects the pending list only */ + spinlock_t lock; + struct list_head pending; + uint32_t sequence; + uint32_t sequence_ack; + uint32_t last_sequence_irq; + } fence; + + /* DMA push buffer */ + struct pscnv_bo *pushbuf; + uint32_t pushbuf_base; + + /* EVO objects */ + struct pscnv_bo *evo_obj; + struct pscnv_ramht evo_ramht; + uint32_t evo_inst; + + /* GPU object info for stuff used in-kernel (mm_enabled) */ + bool accel_done; + + /* Push buffer state (only for drm's channel on !mm_enabled) */ + struct { + int max; + int free; + int cur; + int put; + /* access via pushbuf_bo */ + } dma; + + struct { + bool active; + char name[32]; + struct drm_info_list info; + } debugfs; +}; + +struct nouveau_display_engine { + int (*early_init)(struct drm_device *); + void (*late_takedown)(struct drm_device *); + int (*create)(struct drm_device *); + int (*init)(struct drm_device *); + void (*destroy)(struct drm_device *); +}; + +struct nouveau_gpio_engine { + int (*init)(struct drm_device *); + void (*takedown)(struct drm_device *); + + int (*get)(struct drm_device *, enum dcb_gpio_tag); + int (*set)(struct drm_device *, enum dcb_gpio_tag, int state); + + void (*irq_enable)(struct drm_device *, enum dcb_gpio_tag, bool on); +}; + +struct nouveau_pm_voltage_level { + u8 voltage; + u8 vid; +}; + +struct nouveau_pm_voltage { + bool supported; + u8 vid_mask; + + struct nouveau_pm_voltage_level *level; + int nr_level; +}; + +#define NOUVEAU_PM_MAX_LEVEL 8 +struct nouveau_pm_level { + struct device_attribute dev_attr; + char name[32]; + int id; + + u32 core; + u32 memory; + u32 shader; + u32 unk05; + + u8 voltage; + u8 fanspeed; + + u16 memscript; +}; + +struct nouveau_pm_temp_sensor_constants { + u16 offset_constant; + s16 offset_mult; + u16 offset_div; + u16 slope_mult; + u16 slope_div; +}; + +struct nouveau_pm_threshold_temp { + s16 critical; + s16 down_clock; + s16 fan_boost; +}; + +struct nouveau_pm_memtiming { + u32 reg_100220; + u32 reg_100224; + u32 reg_100228; + u32 reg_10022c; + u32 reg_100230; + u32 reg_100234; + u32 reg_100238; + u32 reg_10023c; +}; + +struct nouveau_pm_memtimings { + bool supported; + struct nouveau_pm_memtiming *timing; + int nr_timing; +}; + +struct nouveau_pm_engine { + struct nouveau_pm_voltage voltage; + struct nouveau_pm_level perflvl[NOUVEAU_PM_MAX_LEVEL]; + int nr_perflvl; + struct nouveau_pm_memtimings memtimings; + struct nouveau_pm_temp_sensor_constants sensor_constants; + struct nouveau_pm_threshold_temp threshold_temp; + + struct nouveau_pm_level boot; + struct nouveau_pm_level *cur; + + struct device *hwmon; + struct notifier_block acpi_nb; + + int (*clock_get)(struct drm_device *, u32 id); + void *(*clock_pre)(struct drm_device *, struct nouveau_pm_level *, + u32 id, int khz); + void (*clock_set)(struct drm_device *, void *); + int (*voltage_get)(struct drm_device *); + int (*voltage_set)(struct drm_device *, int voltage); + int (*fanspeed_get)(struct drm_device *); + int (*fanspeed_set)(struct drm_device *, int fanspeed); + int (*temp_get)(struct drm_device *); +}; + +struct nouveau_engine { + struct nouveau_display_engine display; + struct nouveau_gpio_engine gpio; + struct nouveau_pm_engine pm; +}; + +struct nouveau_pll_vals { + union { + struct { +#ifdef __BIG_ENDIAN + uint8_t N1, M1, N2, M2; +#else + uint8_t M1, N1, M2, N2; +#endif + }; + struct { + uint16_t NM1, NM2; + } __attribute__((packed)); + }; + int log2P; + + int refclk; +}; + +enum nv04_fp_display_regs { + FP_DISPLAY_END, + FP_TOTAL, + FP_CRTC, + FP_SYNC_START, + FP_SYNC_END, + FP_VALID_START, + FP_VALID_END +}; + +struct nv04_crtc_reg { + unsigned char MiscOutReg; + uint8_t CRTC[0xa0]; + uint8_t CR58[0x10]; + uint8_t Sequencer[5]; + uint8_t Graphics[9]; + uint8_t Attribute[21]; + unsigned char DAC[768]; + + /* PCRTC regs */ + uint32_t fb_start; + uint32_t crtc_cfg; + uint32_t cursor_cfg; + uint32_t gpio_ext; + uint32_t crtc_830; + uint32_t crtc_834; + uint32_t crtc_850; + uint32_t crtc_eng_ctrl; + + /* PRAMDAC regs */ + uint32_t nv10_cursync; + struct nouveau_pll_vals pllvals; + uint32_t ramdac_gen_ctrl; + uint32_t ramdac_630; + uint32_t ramdac_634; + uint32_t tv_setup; + uint32_t tv_vtotal; + uint32_t tv_vskew; + uint32_t tv_vsync_delay; + uint32_t tv_htotal; + uint32_t tv_hskew; + uint32_t tv_hsync_delay; + uint32_t tv_hsync_delay2; + uint32_t fp_horiz_regs[7]; + uint32_t fp_vert_regs[7]; + uint32_t dither; + uint32_t fp_control; + uint32_t dither_regs[6]; + uint32_t fp_debug_0; + uint32_t fp_debug_1; + uint32_t fp_debug_2; + uint32_t fp_margin_color; + uint32_t ramdac_8c0; + uint32_t ramdac_a20; + uint32_t ramdac_a24; + uint32_t ramdac_a34; + uint32_t ctv_regs[38]; +}; + +struct nv04_output_reg { + uint32_t output; + int head; +}; + +struct nv04_mode_state { + struct nv04_crtc_reg crtc_reg[2]; + uint32_t pllsel; + uint32_t sel_clk; +}; + +enum nouveau_card_type { + NV_01 = 0x01, + NV_02 = 0x02, + NV_03 = 0x03, + NV_04 = 0x04, + NV_10 = 0x10, + NV_20 = 0x20, + NV_30 = 0x30, + NV_40 = 0x40, + NV_50 = 0x50, + NV_C0 = 0xc0, +}; + +struct drm_nouveau_private { + struct drm_device *dev; + enum { + NOUVEAU_CARD_INIT_DOWN, + NOUVEAU_CARD_INIT_DONE, + NOUVEAU_CARD_INIT_FAILED + } init_state; + + /* the card type, takes NV_* as values */ + enum nouveau_card_type card_type; + /* exact chipset, derived from NV_PMC_BOOT_0 */ + int chipset; + int flags; + + void __iomem *mmio; + void __iomem *ramin; + uint32_t ramin_size; + + struct workqueue_struct *wq; + struct work_struct irq_work; + struct work_struct hpd_work; +#if 0 + struct nouveau_channel *fifos[NOUVEAU_MAX_CHANNEL_NR]; +#endif + struct nouveau_engine engine; + struct pscnv_vram_engine *vram; + struct pscnv_vm_engine *vm; + struct pscnv_chan_engine *chan; + struct pscnv_fifo_engine *fifo; + struct pscnv_engine *engines[PSCNV_ENGINES_NUM]; + int vm_ok; + uint64_t vm_ramin_base; +#if 0 + struct nouveau_channel *channel; +#endif + + spinlock_t irq_lock; + nouveau_irqhandler_t irq_handler[32]; + +#if 0 /* relevant only for pre-NV50 */ + /* RAMIN configuration, RAMFC, RAMHT and RAMRO offsets */ + struct nouveau_gpuobj *ramht; + uint32_t ramin_rsvd_vram; + uint32_t ramht_offset; + uint32_t ramht_size; + uint32_t ramht_bits; + uint32_t ramfc_offset; + uint32_t ramfc_size; + uint32_t ramro_offset; + uint32_t ramro_size; + + struct { + enum { + NOUVEAU_GART_NONE = 0, + NOUVEAU_GART_AGP, + NOUVEAU_GART_SGDMA + } type; + uint64_t aper_base; + uint64_t aper_size; + uint64_t aper_free; + + struct nouveau_gpuobj *sg_ctxdma; + struct page *sg_dummy_page; + dma_addr_t sg_dummy_bus; + } gart_info; + + /* nv10-nv40 tiling regions */ + struct { + struct nouveau_tile_reg reg[NOUVEAU_MAX_TILE_NR]; + spinlock_t lock; + } tile; +#endif + + /* VRAM/fb configuration */ + uint64_t vram_size; + uint64_t vram_sys_base; + + uint64_t fb_size; + uint64_t fb_phys; + int fb_mtrr; + + uint64_t mmio_phys; + + struct pscnv_mm *vram_mm; + struct mutex vram_mutex; + + /* for slow-path nv_wv32/nv_rv32 */ + + spinlock_t pramin_lock; + uint64_t pramin_start; + +#if 0 /* pre-NV50 only */ + struct mem_block *ramin_heap; + + /* context table pointed to be NV_PGRAPH_CHANNEL_CTX_TABLE (0x400780) */ + uint32_t ctx_table_size; + struct nouveau_gpuobj_ref *ctx_table; +#endif + + struct nvbios vbios; + + struct nv04_mode_state mode_reg; + struct nv04_mode_state saved_reg; + uint32_t saved_vga_font[4][16384]; + uint32_t crtc_owner; + uint32_t dac_users[4]; + + struct nouveau_suspend_resume { + uint32_t *ramin_copy; + } susres; + + struct backlight_device *backlight; + + struct nouveau_channel *evo; + struct { + struct dcb_entry *dcb; + u16 script; + u32 pclk; + } evo_irq; + + struct { + struct dentry *channel_root; + } debugfs; + + struct nouveau_fbdev *nfbdev; + struct apertures_struct *apertures; +}; +#if 0 +static inline struct drm_nouveau_private * +nouveau_private(struct drm_device *dev) +{ + return dev->dev_private; +} + +static inline struct drm_nouveau_private * +nouveau_bdev(struct ttm_bo_device *bd) +{ + return container_of(bd, struct drm_nouveau_private, ttm.bdev); +} + +static inline int +nouveau_bo_ref(struct nouveau_bo *ref, struct nouveau_bo **pnvbo) +{ + struct nouveau_bo *prev; + + if (!pnvbo) + return -EINVAL; + prev = *pnvbo; + + *pnvbo = ref ? nouveau_bo(ttm_bo_reference(&ref->bo)) : NULL; + if (prev) { + struct ttm_buffer_object *bo = &prev->bo; + + ttm_bo_unref(&bo); + } + + return 0; +} +#endif +#define NOUVEAU_CHECK_INITIALISED_WITH_RETURN do { \ + struct drm_nouveau_private *nv = dev->dev_private; \ + if (nv->init_state != NOUVEAU_CARD_INIT_DONE) { \ + NV_ERROR(dev, "called without init\n"); \ + return -EINVAL; \ + } \ +} while (0) + +/* nouveau_drv.c */ +extern int nouveau_agpmode; +extern int nouveau_duallink; +extern int nouveau_uscript_lvds; +extern int nouveau_uscript_tmds; +extern int nouveau_vram_pushbuf; +extern int nouveau_vram_notify; +extern int nouveau_fbpercrtc; +extern int nouveau_tv_disable; +extern char *nouveau_tv_norm; +extern int nouveau_reg_debug; +extern int pscnv_mm_debug; +extern int pscnv_mem_debug; +extern int pscnv_vm_debug; +extern int pscnv_gem_debug; +extern int pscnv_ramht_debug; +extern char *nouveau_vbios; +extern int nouveau_ctxfw; +extern int nouveau_ignorelid; +extern int nouveau_nofbaccel; +extern int nouveau_noaccel; +extern int nouveau_force_post; +extern int nouveau_override_conntype; +extern char *nouveau_perflvl; +extern int nouveau_perflvl_wr; + +extern struct drm_ioctl_desc nouveau_ioctls[]; +extern int nouveau_max_ioctl; + +extern int nouveau_pci_suspend(struct pci_dev *pdev, pm_message_t pm_state); +extern int nouveau_pci_resume(struct pci_dev *pdev); + +/* nouveau_state.c */ +extern void nouveau_preclose(struct drm_device *dev, struct drm_file *); +extern int nouveau_load(struct drm_device *, unsigned long flags); +extern int nouveau_firstopen(struct drm_device *); +extern void nouveau_lastclose(struct drm_device *); +extern int nouveau_unload(struct drm_device *); +extern bool nouveau_wait_until(struct drm_device *, uint64_t timeout, + uint32_t reg, uint32_t mask, uint32_t val); +extern bool nouveau_wait_until_neq(struct drm_device *, uint64_t timeout, + uint32_t reg, uint32_t mask, uint32_t val); +//extern bool nouveau_wait_for_idle(struct drm_device *); +extern int nouveau_card_init(struct drm_device *); + +# if 0 + +/* nouveau_mem.c */ +extern int nouveau_mem_init_heap(struct mem_block **, uint64_t start, + uint64_t size); +extern struct mem_block *nouveau_mem_alloc_block(struct mem_block *, + uint64_t size, int align2, + struct drm_file *, int tail); +extern void nouveau_mem_takedown(struct mem_block **heap); +extern void nouveau_mem_free_block(struct mem_block *); +extern int nouveau_mem_detect(struct drm_device *dev); +extern void nouveau_mem_release(struct drm_file *, struct mem_block *heap); +extern int nouveau_mem_init(struct drm_device *); +extern int nouveau_mem_init_agp(struct drm_device *); +extern void nouveau_mem_close(struct drm_device *); +extern struct nouveau_tile_reg *nv10_mem_set_tiling(struct drm_device *dev, + uint32_t addr, + uint32_t size, + uint32_t pitch); +extern void nv10_mem_expire_tiling(struct drm_device *dev, + struct nouveau_tile_reg *tile, + struct nouveau_fence *fence); +extern int nv50_mem_vm_bind_linear(struct drm_device *, uint64_t virt, + uint32_t size, uint32_t flags, + uint64_t phys); +extern void nv50_mem_vm_unbind(struct drm_device *, uint64_t virt, + uint32_t size); + +/* nouveau_notifier.c */ +extern int nouveau_notifier_init_channel(struct nouveau_channel *); +extern void nouveau_notifier_takedown_channel(struct nouveau_channel *); +extern int nouveau_notifier_alloc(struct nouveau_channel *, uint32_t handle, + int cout, uint32_t *offset); +extern int nouveau_notifier_offset(struct nouveau_gpuobj *, uint32_t *); +extern int nouveau_ioctl_notifier_alloc(struct drm_device *, void *data, + struct drm_file *); +extern int nouveau_ioctl_notifier_free(struct drm_device *, void *data, + struct drm_file *); + +/* nouveau_channel.c */ +extern void nouveau_channel_cleanup(struct drm_device *, struct drm_file *); +extern int nouveau_channel_owner(struct drm_device *, struct drm_file *, + int channel); +extern int nouveau_channel_alloc(struct drm_device *dev, + struct nouveau_channel **chan, + struct drm_file *file_priv, + uint32_t fb_ctxdma, uint32_t tt_ctxdma); +extern void nouveau_channel_free(struct nouveau_channel *); + +/* nouveau_object.c */ +extern int nouveau_gpuobj_early_init(struct drm_device *); +extern int nouveau_gpuobj_init(struct drm_device *); +extern void nouveau_gpuobj_takedown(struct drm_device *); +extern void nouveau_gpuobj_late_takedown(struct drm_device *); +extern int nouveau_gpuobj_suspend(struct drm_device *dev); +extern void nouveau_gpuobj_suspend_cleanup(struct drm_device *dev); +extern void nouveau_gpuobj_resume(struct drm_device *dev); +extern int nouveau_gpuobj_channel_init(struct nouveau_channel *, + uint32_t vram_h, uint32_t tt_h); +extern void nouveau_gpuobj_channel_takedown(struct nouveau_channel *); +extern int nouveau_gpuobj_new(struct drm_device *, struct nouveau_channel *, + uint32_t size, int align, uint32_t flags, + struct nouveau_gpuobj **); +extern int nouveau_gpuobj_del(struct drm_device *, struct nouveau_gpuobj **); +extern int nouveau_gpuobj_ref_add(struct drm_device *, struct nouveau_channel *, + uint32_t handle, struct nouveau_gpuobj *, + struct nouveau_gpuobj_ref **); +extern int nouveau_gpuobj_ref_del(struct drm_device *, + struct nouveau_gpuobj_ref **); +extern int nouveau_gpuobj_ref_find(struct nouveau_channel *, uint32_t handle, + struct nouveau_gpuobj_ref **ref_ret); +extern int nouveau_gpuobj_new_ref(struct drm_device *, + struct nouveau_channel *alloc_chan, + struct nouveau_channel *ref_chan, + uint32_t handle, uint32_t size, int align, + uint32_t flags, struct nouveau_gpuobj_ref **); +extern int nouveau_gpuobj_new_fake(struct drm_device *, + uint32_t p_offset, uint32_t b_offset, + uint32_t size, uint32_t flags, + struct nouveau_gpuobj **, + struct nouveau_gpuobj_ref**); +extern int nouveau_gpuobj_dma_new(struct nouveau_channel *, int class, + uint64_t offset, uint64_t size, int access, + int target, struct nouveau_gpuobj **); +extern int nouveau_gpuobj_gart_dma_new(struct nouveau_channel *, + uint64_t offset, uint64_t size, + int access, struct nouveau_gpuobj **, + uint32_t *o_ret); +extern int nouveau_gpuobj_gr_new(struct nouveau_channel *, int class, + struct nouveau_gpuobj **); +extern int nouveau_gpuobj_sw_new(struct nouveau_channel *, int class, + struct nouveau_gpuobj **); +extern int nouveau_ioctl_grobj_alloc(struct drm_device *, void *data, + struct drm_file *); +extern int nouveau_ioctl_gpuobj_free(struct drm_device *, void *data, + struct drm_file *); + +#endif +/* nouveau_irq.c */ +extern irqreturn_t nouveau_irq_handler(DRM_IRQ_ARGS); +extern void nouveau_irq_preinstall(struct drm_device *); +extern int nouveau_irq_postinstall(struct drm_device *); +extern void nouveau_irq_uninstall(struct drm_device *); +extern void nouveau_irq_register(struct drm_device *, int irq, nouveau_irqhandler_t handler); +extern void nouveau_irq_unregister(struct drm_device *, int irq); +#if 0 +/* nouveau_sgdma.c */ +extern int nouveau_sgdma_init(struct drm_device *); +extern void nouveau_sgdma_takedown(struct drm_device *); +extern int nouveau_sgdma_get_page(struct drm_device *, uint32_t offset, + uint32_t *page); +extern struct ttm_backend *nouveau_sgdma_init_ttm(struct drm_device *); + +/* nouveau_debugfs.c */ +#endif +#if defined(CONFIG_DRM_NOUVEAU_DEBUG) +extern int nouveau_debugfs_init(struct drm_minor *); +extern void nouveau_debugfs_takedown(struct drm_minor *); +#if 0 +extern int nouveau_debugfs_channel_init(struct nouveau_channel *); +extern void nouveau_debugfs_channel_fini(struct nouveau_channel *); +#endif +#else +static inline int +nouveau_debugfs_init(struct drm_minor *minor) +{ + return 0; +} + +static inline void nouveau_debugfs_takedown(struct drm_minor *minor) +{ +} +#if 0 +static inline int +nouveau_debugfs_channel_init(struct nouveau_channel *chan) +{ + return 0; +} + +static inline void +nouveau_debugfs_channel_fini(struct nouveau_channel *chan) +{ +} +#endif +#endif + +/* nouveau_acpi.c */ +#define ROM_BIOS_PAGE 4096 +#if defined(CONFIG_ACPI) +void nouveau_register_dsm_handler(void); +void nouveau_unregister_dsm_handler(void); +int nouveau_acpi_get_bios_chunk(uint8_t *bios, int offset, int len); +bool nouveau_acpi_rom_supported(struct pci_dev *pdev); +int nouveau_acpi_edid(struct drm_device *, struct drm_connector *); +#else +static inline void nouveau_register_dsm_handler(void) {} +static inline void nouveau_unregister_dsm_handler(void) {} +static inline bool nouveau_acpi_rom_supported(struct pci_dev *pdev) { return false; } +static inline int nouveau_acpi_get_bios_chunk(uint8_t *bios, int offset, int len) { return -EINVAL; } +static inline int nouveau_acpi_edid(struct drm_device *dev, struct drm_connector *connector) { return -EINVAL; } +#endif + +/* nouveau_backlight.c */ +#ifdef CONFIG_DRM_NOUVEAU_BACKLIGHT +extern int nouveau_backlight_init(struct drm_device *); +extern void nouveau_backlight_exit(struct drm_device *); +#else +static inline int nouveau_backlight_init(struct drm_device *dev) +{ + return 0; +} + +static inline void nouveau_backlight_exit(struct drm_device *dev) { } +#endif + +/* nouveau_bios.c */ +extern int nouveau_bios_init(struct drm_device *); +extern void nouveau_bios_takedown(struct drm_device *dev); +extern int nouveau_run_vbios_init(struct drm_device *); +extern void nouveau_bios_run_init_table(struct drm_device *, uint16_t table, + struct dcb_entry *); +extern struct dcb_gpio_entry *nouveau_bios_gpio_entry(struct drm_device *, + enum dcb_gpio_tag); +extern struct dcb_connector_table_entry * +nouveau_bios_connector_entry(struct drm_device *, int index); +extern u32 get_pll_register(struct drm_device *, enum pll_types); +extern int get_pll_limits(struct drm_device *, uint32_t limit_match, + struct pll_lims *); +extern int nouveau_bios_run_display_table(struct drm_device *, + struct dcb_entry *, + uint32_t script, int pxclk); +extern void *nouveau_bios_dp_table(struct drm_device *, struct dcb_entry *, + int *length); +extern bool nouveau_bios_fp_mode(struct drm_device *, struct drm_display_mode *); +extern uint8_t *nouveau_bios_embedded_edid(struct drm_device *); +extern int nouveau_bios_parse_lvds_table(struct drm_device *, int pxclk, + bool *dl, bool *if_is_24bit); +extern int run_tmds_table(struct drm_device *, struct dcb_entry *, + int head, int pxclk); +extern int call_lvds_script(struct drm_device *, struct dcb_entry *, int head, + enum LVDS_script, int pxclk); + +/* nouveau_dp.c */ +int nouveau_dp_auxch(struct nouveau_i2c_chan *auxch, int cmd, int addr, + uint8_t *data, int data_nr); +bool nouveau_dp_detect(struct drm_encoder *); +bool nouveau_dp_link_train(struct drm_encoder *); + +/* nv04_fb.c */ +extern int nv04_fb_init(struct drm_device *); +extern void nv04_fb_takedown(struct drm_device *); + +/* nv10_fb.c */ +extern int nv10_fb_init(struct drm_device *); +extern void nv10_fb_takedown(struct drm_device *); +extern void nv10_fb_set_region_tiling(struct drm_device *, int, uint32_t, + uint32_t, uint32_t); + +/* nv40_fb.c */ +extern int nv40_fb_init(struct drm_device *); +extern void nv40_fb_takedown(struct drm_device *); +extern void nv40_fb_set_region_tiling(struct drm_device *, int, uint32_t, + uint32_t, uint32_t); +/* nv50_fb.c */ +extern int nv50_fb_init(struct drm_device *); +extern void nv50_fb_takedown(struct drm_device *); + +/* nv50_fb.c */ +extern int nv50_fb_init(struct drm_device *); +extern void nv50_fb_takedown(struct drm_device *); +#if 0 +/* nv04_fifo.c */ +extern int nv04_fifo_init(struct drm_device *); +extern void nv04_fifo_disable(struct drm_device *); +extern void nv04_fifo_enable(struct drm_device *); +extern bool nv04_fifo_reassign(struct drm_device *, bool); +extern bool nv04_fifo_cache_flush(struct drm_device *); +extern bool nv04_fifo_cache_pull(struct drm_device *, bool); +extern int nv04_fifo_channel_id(struct drm_device *); +extern int nv04_fifo_create_context(struct nouveau_channel *); +extern void nv04_fifo_destroy_context(struct nouveau_channel *); +extern int nv04_fifo_load_context(struct nouveau_channel *); +extern int nv04_fifo_unload_context(struct drm_device *); + +/* nv10_fifo.c */ +extern int nv10_fifo_init(struct drm_device *); +extern int nv10_fifo_channel_id(struct drm_device *); +extern int nv10_fifo_create_context(struct nouveau_channel *); +extern void nv10_fifo_destroy_context(struct nouveau_channel *); +extern int nv10_fifo_load_context(struct nouveau_channel *); +extern int nv10_fifo_unload_context(struct drm_device *); + +/* nv40_fifo.c */ +extern int nv40_fifo_init(struct drm_device *); +extern int nv40_fifo_create_context(struct nouveau_channel *); +extern void nv40_fifo_destroy_context(struct nouveau_channel *); +extern int nv40_fifo_load_context(struct nouveau_channel *); +extern int nv40_fifo_unload_context(struct drm_device *); + +/* nv50_fifo.c */ +extern int nv50_fifo_init(struct drm_device *); +extern void nv50_fifo_takedown(struct drm_device *); +extern int nv50_fifo_channel_id(struct drm_device *); +extern int nv50_fifo_create_context(struct nouveau_channel *); +extern void nv50_fifo_destroy_context(struct nouveau_channel *); +extern int nv50_fifo_load_context(struct nouveau_channel *); +extern int nv50_fifo_unload_context(struct drm_device *); + +/* nv04_graph.c */ +extern struct nouveau_pgraph_object_class nv04_graph_grclass[]; +extern int nv04_graph_init(struct drm_device *); +extern void nv04_graph_takedown(struct drm_device *); +extern void nv04_graph_fifo_access(struct drm_device *, bool); +extern struct nouveau_channel *nv04_graph_channel(struct drm_device *); +extern int nv04_graph_create_context(struct nouveau_channel *); +extern void nv04_graph_destroy_context(struct nouveau_channel *); +extern int nv04_graph_load_context(struct nouveau_channel *); +extern int nv04_graph_unload_context(struct drm_device *); +extern void nv04_graph_context_switch(struct drm_device *); + +/* nv10_graph.c */ +extern struct nouveau_pgraph_object_class nv10_graph_grclass[]; +extern int nv10_graph_init(struct drm_device *); +extern void nv10_graph_takedown(struct drm_device *); +extern struct nouveau_channel *nv10_graph_channel(struct drm_device *); +extern int nv10_graph_create_context(struct nouveau_channel *); +extern void nv10_graph_destroy_context(struct nouveau_channel *); +extern int nv10_graph_load_context(struct nouveau_channel *); +extern int nv10_graph_unload_context(struct drm_device *); +extern void nv10_graph_context_switch(struct drm_device *); +extern void nv10_graph_set_region_tiling(struct drm_device *, int, uint32_t, + uint32_t, uint32_t); + +/* nv20_graph.c */ +extern struct nouveau_pgraph_object_class nv20_graph_grclass[]; +extern struct nouveau_pgraph_object_class nv30_graph_grclass[]; +extern int nv20_graph_create_context(struct nouveau_channel *); +extern void nv20_graph_destroy_context(struct nouveau_channel *); +extern int nv20_graph_load_context(struct nouveau_channel *); +extern int nv20_graph_unload_context(struct drm_device *); +extern int nv20_graph_init(struct drm_device *); +extern void nv20_graph_takedown(struct drm_device *); +extern int nv30_graph_init(struct drm_device *); +extern void nv20_graph_set_region_tiling(struct drm_device *, int, uint32_t, + uint32_t, uint32_t); + +/* nv40_graph.c */ +extern struct nouveau_pgraph_object_class nv40_graph_grclass[]; +extern int nv40_graph_init(struct drm_device *); +extern void nv40_graph_takedown(struct drm_device *); +extern struct nouveau_channel *nv40_graph_channel(struct drm_device *); +extern int nv40_graph_create_context(struct nouveau_channel *); +extern void nv40_graph_destroy_context(struct nouveau_channel *); +extern int nv40_graph_load_context(struct nouveau_channel *); +extern int nv40_graph_unload_context(struct drm_device *); +extern void nv40_grctx_init(struct nouveau_grctx *); +extern void nv40_graph_set_region_tiling(struct drm_device *, int, uint32_t, + uint32_t, uint32_t); + +/* nv50_graph.c */ +extern struct nouveau_pgraph_object_class nv50_graph_grclass[]; +extern int nv50_graph_init(struct drm_device *); +extern void nv50_graph_takedown(struct drm_device *); +extern void nv50_graph_fifo_access(struct drm_device *, bool); +extern struct nouveau_channel *nv50_graph_channel(struct drm_device *); +extern int nv50_graph_create_context(struct nouveau_channel *); +extern void nv50_graph_destroy_context(struct nouveau_channel *); +extern int nv50_graph_load_context(struct nouveau_channel *); +extern int nv50_graph_unload_context(struct drm_device *); +extern void nv50_graph_context_switch(struct drm_device *); +extern int nv50_grctx_init(struct nouveau_grctx *); + +/* nouveau_grctx.c */ +extern int nouveau_grctx_prog_load(struct drm_device *); +extern void nouveau_grctx_vals_load(struct drm_device *, + struct nouveau_gpuobj *); +extern void nouveau_grctx_fini(struct drm_device *); + +/* nv04_instmem.c */ +extern int nv04_instmem_init(struct drm_device *); +extern void nv04_instmem_takedown(struct drm_device *); +extern int nv04_instmem_suspend(struct drm_device *); +extern void nv04_instmem_resume(struct drm_device *); +extern int nv04_instmem_populate(struct drm_device *, struct nouveau_gpuobj *, + uint32_t *size); +extern void nv04_instmem_clear(struct drm_device *, struct nouveau_gpuobj *); +extern int nv04_instmem_bind(struct drm_device *, struct nouveau_gpuobj *); +extern int nv04_instmem_unbind(struct drm_device *, struct nouveau_gpuobj *); +extern void nv04_instmem_prepare_access(struct drm_device *, bool write); +extern void nv04_instmem_finish_access(struct drm_device *); + +/* nv50_instmem.c */ +extern int nv50_instmem_init(struct drm_device *); +extern void nv50_instmem_takedown(struct drm_device *); +extern int nv50_instmem_suspend(struct drm_device *); +extern void nv50_instmem_resume(struct drm_device *); +extern int nv50_instmem_populate(struct drm_device *, struct nouveau_gpuobj *, + uint32_t *size); +extern void nv50_instmem_clear(struct drm_device *, struct nouveau_gpuobj *); +extern int nv50_instmem_bind(struct drm_device *, struct nouveau_gpuobj *); +extern int nv50_instmem_unbind(struct drm_device *, struct nouveau_gpuobj *); +extern void nv50_instmem_prepare_access(struct drm_device *, bool write); +extern void nv50_instmem_finish_access(struct drm_device *); + +#endif +/* nv04_mc.c */ +extern int nv04_mc_init(struct drm_device *); +extern void nv04_mc_takedown(struct drm_device *); + +/* nv40_mc.c */ +extern int nv40_mc_init(struct drm_device *); +extern void nv40_mc_takedown(struct drm_device *); + +/* nv50_mc.c */ +extern int nv50_mc_init(struct drm_device *); +extern void nv50_mc_takedown(struct drm_device *); + +/* nv04_timer.c */ +extern int nv04_timer_init(struct drm_device *); +extern uint64_t nv04_timer_read(struct drm_device *); + +extern long nouveau_compat_ioctl(struct file *file, unsigned int cmd, + unsigned long arg); + +/* nv04_dac.c */ +extern int nv04_dac_create(struct drm_connector *, struct dcb_entry *); +extern uint32_t nv17_dac_sample_load(struct drm_encoder *encoder); +extern int nv04_dac_output_offset(struct drm_encoder *encoder); +extern void nv04_dac_update_dacclk(struct drm_encoder *encoder, bool enable); +extern bool nv04_dac_in_use(struct drm_encoder *encoder); + +/* nv04_dfp.c */ +extern int nv04_dfp_create(struct drm_connector *, struct dcb_entry *); +extern int nv04_dfp_get_bound_head(struct drm_device *dev, struct dcb_entry *dcbent); +extern void nv04_dfp_bind_head(struct drm_device *dev, struct dcb_entry *dcbent, + int head, bool dl); +extern void nv04_dfp_disable(struct drm_device *dev, int head); +extern void nv04_dfp_update_fp_control(struct drm_encoder *encoder, int mode); + +/* nv04_tv.c */ +extern int nv04_tv_identify(struct drm_device *dev, int i2c_index); +extern int nv04_tv_create(struct drm_connector *, struct dcb_entry *); + +/* nv17_tv.c */ +extern int nv17_tv_create(struct drm_connector *, struct dcb_entry *); + +/* nv04_display.c */ +extern int nv04_display_early_init(struct drm_device *); +extern void nv04_display_late_takedown(struct drm_device *); +extern int nv04_display_create(struct drm_device *); +extern int nv04_display_init(struct drm_device *); +extern void nv04_display_destroy(struct drm_device *); + +/* nv04_crtc.c */ +extern int nv04_crtc_create(struct drm_device *, int index); + +#if 0 +/* nouveau_bo.c */ +extern struct ttm_bo_driver nouveau_bo_driver; +extern int nouveau_bo_new(struct drm_device *, struct nouveau_channel *, + int size, int align, uint32_t flags, + uint32_t tile_mode, uint32_t tile_flags, + bool no_vm, bool mappable, struct nouveau_bo **); +extern int nouveau_bo_pin(struct nouveau_bo *, uint32_t flags); +extern int nouveau_bo_unpin(struct nouveau_bo *); +extern int nouveau_bo_map(struct nouveau_bo *); +extern void nouveau_bo_unmap(struct nouveau_bo *); +extern void nouveau_bo_placement_set(struct nouveau_bo *, uint32_t type, + uint32_t busy); +extern u16 nouveau_bo_rd16(struct nouveau_bo *nvbo, unsigned index); +extern void nouveau_bo_wr16(struct nouveau_bo *nvbo, unsigned index, u16 val); +extern u32 nouveau_bo_rd32(struct nouveau_bo *nvbo, unsigned index); +extern void nouveau_bo_wr32(struct nouveau_bo *nvbo, unsigned index, u32 val); + +/* nouveau_fence.c */ +struct nouveau_fence; +extern int nouveau_fence_init(struct nouveau_channel *); +extern void nouveau_fence_fini(struct nouveau_channel *); +extern void nouveau_fence_update(struct nouveau_channel *); +extern int nouveau_fence_new(struct nouveau_channel *, struct nouveau_fence **, + bool emit); +extern int nouveau_fence_emit(struct nouveau_fence *); +struct nouveau_channel *nouveau_fence_channel(struct nouveau_fence *); +extern bool nouveau_fence_signalled(void *obj, void *arg); +extern int nouveau_fence_wait(void *obj, void *arg, bool lazy, bool intr); +extern int nouveau_fence_flush(void *obj, void *arg); +extern void nouveau_fence_unref(void **obj); +extern void *nouveau_fence_ref(void *obj); +extern void nouveau_fence_handler(struct drm_device *dev, int channel); + +#endif +/* nv10_gpio.c */ +int nv10_gpio_get(struct drm_device *dev, enum dcb_gpio_tag tag); +int nv10_gpio_set(struct drm_device *dev, enum dcb_gpio_tag tag, int state); + +/* nv50_gpio.c */ +int nv50_gpio_init(struct drm_device *dev); +int nv50_gpio_get(struct drm_device *dev, enum dcb_gpio_tag tag); +int nv50_gpio_set(struct drm_device *dev, enum dcb_gpio_tag tag, int state); +void nv50_gpio_irq_enable(struct drm_device *, enum dcb_gpio_tag, bool on); + +/* nv50_calc. */ +int nv50_calc_pll(struct drm_device *, struct pll_lims *, int clk, + int *N1, int *M1, int *N2, int *M2, int *P); +int nv50_calc_pll2(struct drm_device *, struct pll_lims *, + int clk, int *N, int *fN, int *M, int *P); + +#ifndef ioread32_native +#ifdef __BIG_ENDIAN +#define ioread16_native ioread16be +#define iowrite16_native iowrite16be +#define ioread32_native ioread32be +#define iowrite32_native iowrite32be +#else /* def __BIG_ENDIAN */ +#define ioread16_native ioread16 +#define iowrite16_native iowrite16 +#define ioread32_native ioread32 +#define iowrite32_native iowrite32 +#endif /* def __BIG_ENDIAN else */ +#endif /* !ioread32_native */ + +#if 0 +/* channel control reg access */ +static inline u32 nvchan_rd32(struct nouveau_channel *chan, unsigned reg) +{ + return ioread32_native(chan->user + reg); +} + +static inline void nvchan_wr32(struct nouveau_channel *chan, + unsigned reg, u32 val) +{ + iowrite32_native(val, chan->user + reg); +} +#endif + +/* register access */ +static inline u32 nv_rd32(struct drm_device *dev, unsigned reg) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + return ioread32_native(dev_priv->mmio + reg); +} + +static inline void nv_wr32(struct drm_device *dev, unsigned reg, u32 val) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + iowrite32_native(val, dev_priv->mmio + reg); +} + +static inline u32 nv_mask(struct drm_device *dev, u32 reg, u32 mask, u32 val) +{ + u32 tmp = nv_rd32(dev, reg); + nv_wr32(dev, reg, (tmp & ~mask) | val); + return tmp; +} + +static inline u8 nv_rd08(struct drm_device *dev, unsigned reg) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + return ioread8(dev_priv->mmio + reg); +} + +static inline void nv_wr08(struct drm_device *dev, unsigned reg, u8 val) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + iowrite8(val, dev_priv->mmio + reg); +} + +#define nv_wait(dev, reg, mask, val) \ + nouveau_wait_until(dev, 2000000000ULL, (reg), (mask), (val)) + +#define nv_wait_neq(dev, reg, mask, val) \ + nouveau_wait_until_neq(dev, 2000000000ULL, (reg), (mask), (val)) + +#if 0 /* not removing yet - may be useful for pre-NV50 one day */ +/* PRAMIN access */ +static inline u32 nv_ri32(struct drm_device *dev, unsigned offset) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + return ioread32_native(dev_priv->ramin + offset); +} + +static inline void nv_wi32(struct drm_device *dev, unsigned offset, u32 val) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + iowrite32_native(val, dev_priv->ramin + offset); +} +#endif +/* + * Logging + * Argument d is (struct drm_device *). + */ +#define NV_PRINTK(level, d, fmt, arg...) \ + printk(level "[" DRM_NAME "] " DRIVER_NAME " %s: " fmt, \ + pci_name(d->pdev), ##arg) +#ifndef NV_DEBUG_NOTRACE +#define NV_DEBUG(d, fmt, arg...) do { \ + if (drm_debug & DRM_UT_DRIVER) { \ + NV_PRINTK(KERN_DEBUG, d, "%s:%d - " fmt, __func__, \ + __LINE__, ##arg); \ + } \ +} while (0) +#define NV_DEBUG_KMS(d, fmt, arg...) do { \ + if (drm_debug & DRM_UT_KMS) { \ + NV_PRINTK(KERN_DEBUG, d, "%s:%d - " fmt, __func__, \ + __LINE__, ##arg); \ + } \ +} while (0) +#else +#define NV_DEBUG(d, fmt, arg...) do { \ + if (drm_debug & DRM_UT_DRIVER) \ + NV_PRINTK(KERN_DEBUG, d, fmt, ##arg); \ +} while (0) +#define NV_DEBUG_KMS(d, fmt, arg...) do { \ + if (drm_debug & DRM_UT_KMS) \ + NV_PRINTK(KERN_DEBUG, d, fmt, ##arg); \ +} while (0) +#endif +#define NV_ERROR(d, fmt, arg...) NV_PRINTK(KERN_ERR, d, fmt, ##arg) +#define NV_INFO(d, fmt, arg...) NV_PRINTK(KERN_INFO, d, fmt, ##arg) +#define NV_TRACEWARN(d, fmt, arg...) NV_PRINTK(KERN_NOTICE, d, fmt, ##arg) +#define NV_TRACE(d, fmt, arg...) NV_PRINTK(KERN_INFO, d, fmt, ##arg) +#define NV_WARN(d, fmt, arg...) NV_PRINTK(KERN_WARNING, d, fmt, ##arg) + +/* nouveau_reg_debug bitmask */ +enum { + NOUVEAU_REG_DEBUG_MC = 0x1, + NOUVEAU_REG_DEBUG_VIDEO = 0x2, + NOUVEAU_REG_DEBUG_FB = 0x4, + NOUVEAU_REG_DEBUG_EXTDEV = 0x8, + NOUVEAU_REG_DEBUG_CRTC = 0x10, + NOUVEAU_REG_DEBUG_RAMDAC = 0x20, + NOUVEAU_REG_DEBUG_VGACRTC = 0x40, + NOUVEAU_REG_DEBUG_RMVIO = 0x80, + NOUVEAU_REG_DEBUG_VGAATTR = 0x100, + NOUVEAU_REG_DEBUG_EVO = 0x200, +}; + +#define NV_REG_DEBUG(type, dev, fmt, arg...) do { \ + if (nouveau_reg_debug & NOUVEAU_REG_DEBUG_##type) \ + NV_PRINTK(KERN_DEBUG, dev, "%s: " fmt, __func__, ##arg); \ +} while (0) + +static inline bool +nv_two_heads(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + const int impl = dev->pci_device & 0x0ff0; + + if (dev_priv->card_type >= NV_10 && impl != 0x0100 && + impl != 0x0150 && impl != 0x01a0 && impl != 0x0200) + return true; + + return false; +} + +static inline bool +nv_gf4_disp_arch(struct drm_device *dev) +{ + return nv_two_heads(dev) && (dev->pci_device & 0x0ff0) != 0x0110; +} + +static inline bool +nv_two_reg_pll(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + const int impl = dev->pci_device & 0x0ff0; + + if (impl == 0x0310 || impl == 0x0340 || dev_priv->card_type >= NV_40) + return true; + return false; +} + +static inline bool +nv_match_device(struct drm_device *dev, unsigned device, + unsigned sub_vendor, unsigned sub_device) +{ + return dev->pdev->device == device && + dev->pdev->subsystem_vendor == sub_vendor && + dev->pdev->subsystem_device == sub_device; +} + +#if 0 +#define NV_SW 0x0000506e +#define NV_SW_DMA_SEMAPHORE 0x00000060 +#define NV_SW_SEMAPHORE_OFFSET 0x00000064 +#define NV_SW_SEMAPHORE_ACQUIRE 0x00000068 +#define NV_SW_SEMAPHORE_RELEASE 0x0000006c +#define NV_SW_YIELD 0x00000080 +#define NV_SW_DMA_VBLSEM 0x0000018c +#define NV_SW_VBLSEM_OFFSET 0x00000400 +#define NV_SW_VBLSEM_RELEASE_VALUE 0x00000404 +#define NV_SW_VBLSEM_RELEASE 0x00000408 + +#endif + +/* object access */ + +static inline uint32_t nv_rv32(struct pscnv_bo *bo, + unsigned offset) +{ + struct drm_nouveau_private *dev_priv = bo->dev->dev_private; + uint32_t res; + uint64_t addr = bo->start + offset; + if (bo->map3 && dev_priv->vm && dev_priv->vm_ok) + return ioread32_native(dev_priv->ramin + bo->map3->start - dev_priv->vm_ramin_base + offset); + spin_lock(&dev_priv->pramin_lock); + if (addr >> 16 != dev_priv->pramin_start) { + dev_priv->pramin_start = addr >> 16; + nv_wr32(bo->dev, 0x1700, addr >> 16); + } + res = nv_rd32(bo->dev, 0x700000 + (addr & 0xffff)); + spin_unlock(&dev_priv->pramin_lock); + return res; +} + +static inline void nv_wv32(struct pscnv_bo *bo, + unsigned offset, uint32_t val) +{ + struct drm_nouveau_private *dev_priv = bo->dev->dev_private; + uint64_t addr = bo->start + offset; + if (bo->map3 && dev_priv->vm && dev_priv->vm_ok) + return iowrite32_native(val, dev_priv->ramin + bo->map3->start - dev_priv->vm_ramin_base + offset); + spin_lock(&dev_priv->pramin_lock); + if (addr >> 16 != dev_priv->pramin_start) { + dev_priv->pramin_start = addr >> 16; + nv_wr32(bo->dev, 0x1700, addr >> 16); + } + nv_wr32(bo->dev, 0x700000 + (addr & 0xffff), val); + spin_unlock(&dev_priv->pramin_lock); +} + +#endif /* __NOUVEAU_DRV_H__ */ diff --git a/driver/pscnv/nouveau_encoder.h b/driver/pscnv/nouveau_encoder.h new file mode 100644 index 00000000..ae69b61d --- /dev/null +++ b/driver/pscnv/nouveau_encoder.h @@ -0,0 +1,103 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#ifndef __NOUVEAU_ENCODER_H__ +#define __NOUVEAU_ENCODER_H__ + +#include "drm_encoder_slave.h" +#include "nouveau_drv.h" + +#define NV_DPMS_CLEARED 0x80 + +struct nouveau_encoder { + struct drm_encoder_slave base; + + struct dcb_entry *dcb; + int or; + + /* different to drm_encoder.crtc, this reflects what's + * actually programmed on the hw, not the proposed crtc */ + struct drm_crtc *crtc; + + struct drm_display_mode mode; + int last_dpms; + + struct nv04_output_reg restore; + + union { + struct { + int mc_unknown; + uint32_t unk0; + uint32_t unk1; + int dpcd_version; + int link_nr; + int link_bw; + bool enhanced_frame; + } dp; + }; +}; + +static inline struct nouveau_encoder *nouveau_encoder(struct drm_encoder *enc) +{ + struct drm_encoder_slave *slave = to_encoder_slave(enc); + + return container_of(slave, struct nouveau_encoder, base); +} + +static inline struct drm_encoder *to_drm_encoder(struct nouveau_encoder *enc) +{ + return &enc->base.base; +} + +static inline struct drm_encoder_slave_funcs * +get_slave_funcs(struct drm_encoder *enc) +{ + return to_encoder_slave(enc)->slave_funcs; +} + +struct nouveau_connector * +nouveau_encoder_connector_get(struct nouveau_encoder *encoder); +int nv50_sor_create(struct drm_connector *, struct dcb_entry *); +int nv50_dac_create(struct drm_connector *, struct dcb_entry *); + +struct bit_displayport_encoder_table { + uint32_t match; + uint8_t record_nr; + uint8_t unknown; + uint16_t script0; + uint16_t script1; + uint16_t unknown_table; +} __attribute__ ((packed)); + +struct bit_displayport_encoder_table_entry { + uint8_t vs_level; + uint8_t pre_level; + uint8_t reg0; + uint8_t reg1; + uint8_t reg2; +} __attribute__ ((packed)); + +#endif /* __NOUVEAU_ENCODER_H__ */ diff --git a/driver/pscnv/nouveau_fb.h b/driver/pscnv/nouveau_fb.h new file mode 100644 index 00000000..6ee9f0b9 --- /dev/null +++ b/driver/pscnv/nouveau_fb.h @@ -0,0 +1,46 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#ifndef __NOUVEAU_FB_H__ +#define __NOUVEAU_FB_H__ + +struct nouveau_framebuffer { + struct drm_framebuffer base; + struct pscnv_bo *nvbo; +}; + +static inline struct nouveau_framebuffer * +nouveau_framebuffer(struct drm_framebuffer *fb) +{ + return container_of(fb, struct nouveau_framebuffer, base); +} + +extern const struct drm_mode_config_funcs nouveau_mode_config_funcs; + +int nouveau_framebuffer_init(struct drm_device *dev, struct nouveau_framebuffer *nouveau_fb, + struct drm_mode_fb_cmd *mode_cmd, struct pscnv_bo *nvbo); + +#endif /* __NOUVEAU_FB_H__ */ diff --git a/driver/pscnv/nouveau_fbcon.c b/driver/pscnv/nouveau_fbcon.c new file mode 100644 index 00000000..ba5dcbcf --- /dev/null +++ b/driver/pscnv/nouveau_fbcon.c @@ -0,0 +1,444 @@ +/* + * Copyright © 2007 David Airlie + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + * + * Authors: + * David Airlie + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "drmP.h" +#include "drm.h" +#include "drm_crtc.h" +#include "drm_crtc_helper.h" +#include "drm_fb_helper.h" +#include "nouveau_drv.h" +#include "nouveau_crtc.h" +#include "nouveau_fb.h" +#include "nouveau_fbcon.h" +#include "nouveau_dma.h" +#include "pscnv_gem.h" +#include "pscnv_vm.h" + + +static int +nouveau_fbcon_sync(struct fb_info *info) +{ +#if 0 + struct nouveau_fbdev *nfbdev = info->par; + struct drm_device *dev = nfbdev->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *chan = dev_priv->channel; + int ret, i; + + if (!chan || !chan->accel_done || in_interrupt() || + info->state != FBINFO_STATE_RUNNING || + info->flags & FBINFO_HWACCEL_DISABLED) + return 0; + + if (!mutex_trylock(&chan->mutex)) + return 0; + + ret = RING_SPACE(chan, 4); + if (ret) { + mutex_unlock(&chan->mutex); + nouveau_fbcon_gpu_lockup(info); + return 0; + } + + BEGIN_RING(chan, 0, 0x0104, 1); + OUT_RING(chan, 0); + BEGIN_RING(chan, 0, 0x0100, 1); + OUT_RING(chan, 0); + nouveau_bo_wr32(chan->notifier_bo, chan->m2mf_ntfy + 3, 0xffffffff); + FIRE_RING(chan); + mutex_unlock(&chan->mutex); + + ret = -EBUSY; + for (i = 0; i < 100000; i++) { + if (!nouveau_bo_rd32(chan->notifier_bo, chan->m2mf_ntfy + 3)) { + ret = 0; + break; + } + DRM_UDELAY(1); + } + + if (ret) { + nouveau_fbcon_gpu_lockup(info); + return 0; + } + + chan->accel_done = false; +#endif + return 0; +} + +static struct fb_ops nouveau_fbcon_ops = { + .owner = THIS_MODULE, + .fb_check_var = drm_fb_helper_check_var, + .fb_set_par = drm_fb_helper_set_par, + .fb_fillrect = cfb_fillrect, + .fb_copyarea = cfb_copyarea, + .fb_imageblit = cfb_imageblit, + .fb_sync = nouveau_fbcon_sync, + .fb_pan_display = drm_fb_helper_pan_display, + .fb_blank = drm_fb_helper_blank, + .fb_setcmap = drm_fb_helper_setcmap, +}; +#if 0 +static struct fb_ops nv04_fbcon_ops = { + .owner = THIS_MODULE, + .fb_check_var = drm_fb_helper_check_var, + .fb_set_par = drm_fb_helper_set_par, + .fb_fillrect = nv04_fbcon_fillrect, + .fb_copyarea = nv04_fbcon_copyarea, + .fb_imageblit = nv04_fbcon_imageblit, + .fb_sync = nouveau_fbcon_sync, + .fb_pan_display = drm_fb_helper_pan_display, + .fb_blank = drm_fb_helper_blank, + .fb_setcmap = drm_fb_helper_setcmap, +}; + +static struct fb_ops nv50_fbcon_ops = { + .owner = THIS_MODULE, + .fb_check_var = drm_fb_helper_check_var, + .fb_set_par = drm_fb_helper_set_par, + .fb_fillrect = nv50_fbcon_fillrect, + .fb_copyarea = nv50_fbcon_copyarea, + .fb_imageblit = nv50_fbcon_imageblit, + .fb_sync = nouveau_fbcon_sync, + .fb_pan_display = drm_fb_helper_pan_display, + .fb_blank = drm_fb_helper_blank, + .fb_setcmap = drm_fb_helper_setcmap, +}; +#endif +static void nouveau_fbcon_gamma_set(struct drm_crtc *crtc, u16 red, u16 green, + u16 blue, int regno) +{ + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + + nv_crtc->lut.r[regno] = red; + nv_crtc->lut.g[regno] = green; + nv_crtc->lut.b[regno] = blue; +} + +static void nouveau_fbcon_gamma_get(struct drm_crtc *crtc, u16 *red, u16 *green, + u16 *blue, int regno) +{ + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + + *red = nv_crtc->lut.r[regno]; + *green = nv_crtc->lut.g[regno]; + *blue = nv_crtc->lut.b[regno]; +} + +static void +nouveau_fbcon_zfill(struct drm_device *dev, struct nouveau_fbdev *nfbdev) +{ + struct fb_info *info = nfbdev->helper.fbdev; + struct fb_fillrect rect; + + /* Clear the entire fbcon. The drm will program every connector + * with it's preferred mode. If the sizes differ, one display will + * quite likely have garbage around the console. + */ + rect.dx = rect.dy = 0; + rect.width = info->var.xres_virtual; + rect.height = info->var.yres_virtual; + rect.color = 0; + rect.rop = ROP_COPY; + info->fbops->fb_fillrect(info, &rect); +} + +static int +nouveau_fbcon_create(struct nouveau_fbdev *nfbdev, + struct drm_fb_helper_surface_size *sizes) +{ + struct drm_device *dev = nfbdev->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct fb_info *info; + struct drm_framebuffer *fb; + struct nouveau_framebuffer *nouveau_fb; + struct pscnv_bo *nvbo; + struct drm_gem_object *obj; + struct drm_mode_fb_cmd mode_cmd; + struct pci_dev *pdev = dev->pdev; + struct device *device = &pdev->dev; + int size, ret; + + mode_cmd.width = sizes->surface_width; + mode_cmd.height = sizes->surface_height; + + mode_cmd.bpp = sizes->surface_bpp; + mode_cmd.pitch = mode_cmd.width * (mode_cmd.bpp >> 3); + mode_cmd.pitch = roundup(mode_cmd.pitch, 256); + mode_cmd.depth = sizes->surface_depth; + + size = mode_cmd.pitch * mode_cmd.height; + size = roundup(size, PAGE_SIZE); + + obj = pscnv_gem_new(dev, size, PSCNV_GEM_CONTIG, 0, 0xd15fb, 0); + if (!obj) { + ret = -ENOMEM; + NV_ERROR(dev, "failed to allocate framebuffer\n"); + goto out; + } + nvbo = obj->driver_private; + + ret = dev_priv->vm->map_user(nvbo); + if (ret) { + NV_ERROR(dev, "failed to map fb: %d\n", ret); + pscnv_mem_free(nvbo); + goto out; + } + + mutex_lock(&dev->struct_mutex); + + info = framebuffer_alloc(0, device); + if (!info) { + ret = -ENOMEM; + goto out_unref; + } + + ret = fb_alloc_cmap(&info->cmap, 256, 0); + if (ret) { + ret = -ENOMEM; + goto out_unref; + } + + info->par = nfbdev; + + nouveau_framebuffer_init(dev, &nfbdev->nouveau_fb, &mode_cmd, nvbo); + + nouveau_fb = &nfbdev->nouveau_fb; + fb = &nouveau_fb->base; + + /* setup helper */ + nfbdev->helper.fb = fb; + nfbdev->helper.fbdev = info; + + strcpy(info->fix.id, "nouveaufb"); + if (nouveau_nofbaccel) + info->flags = FBINFO_DEFAULT | FBINFO_HWACCEL_DISABLED; + else + info->flags = FBINFO_DEFAULT | FBINFO_HWACCEL_COPYAREA | + FBINFO_HWACCEL_FILLRECT | + FBINFO_HWACCEL_IMAGEBLIT; +#ifdef FBINFO_CAN_FORCE_OUTPUT + info->flags |= FBINFO_CAN_FORCE_OUTPUT; +#endif + info->fbops = &nouveau_fbcon_ops; + info->fix.smem_start = dev->mode_config.fb_base + nvbo->map1->start; + info->fix.smem_len = size; + + info->screen_base = ioremap_wc(dev_priv->fb_phys + nvbo->map1->start, size); + info->screen_size = size; + + drm_fb_helper_fill_fix(info, fb->pitch, fb->depth); + drm_fb_helper_fill_var(info, &nfbdev->helper, sizes->fb_width, sizes->fb_height); + + /* FIXME: we really shouldn't expose mmio space at all */ + info->fix.mmio_start = pci_resource_start(pdev, 1); + info->fix.mmio_len = pci_resource_len(pdev, 1); + + /* Set aperture base/size for vesafb takeover */ + info->apertures = dev_priv->apertures; + if (!info->apertures) { + ret = -ENOMEM; + goto out_unref; + } + + info->pixmap.size = 64*1024; + info->pixmap.buf_align = 8; + info->pixmap.access_align = 32; + info->pixmap.flags = FB_PIXMAP_SYSTEM; + info->pixmap.scan_align = 1; + + mutex_unlock(&dev->struct_mutex); +#if 0 + if (dev_priv->channel && !nouveau_nofbaccel) { + switch (dev_priv->card_type) { + case NV_50: + nv50_fbcon_accel_init(info); + info->fbops = &nv50_fbcon_ops; + break; + default: + nv04_fbcon_accel_init(info); + info->fbops = &nv04_fbcon_ops; + break; + }; + } +#endif + nouveau_fbcon_zfill(dev, nfbdev); + + /* To allow resizeing without swapping buffers */ + NV_INFO(dev, "allocated %dx%d fb: 0x%llx 0x%llx, bo %p\n", + nouveau_fb->base.width, + nouveau_fb->base.height, + nvbo->start, nvbo->map1->start, nvbo); + + vga_switcheroo_client_fb_set(dev->pdev, info); + return 0; + +out_unref: + mutex_unlock(&dev->struct_mutex); +out: + return ret; +} + +static int +nouveau_fbcon_find_or_create_single(struct drm_fb_helper *helper, + struct drm_fb_helper_surface_size *sizes) +{ + struct nouveau_fbdev *nfbdev = (struct nouveau_fbdev *)helper; + int new_fb = 0; + int ret; + + if (!helper->fb) { + ret = nouveau_fbcon_create(nfbdev, sizes); + if (ret) + return ret; + new_fb = 1; + } + return new_fb; +} + +void +nouveau_fbcon_output_poll_changed(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + drm_fb_helper_hotplug_event(&dev_priv->nfbdev->helper); +} + +static int +nouveau_fbcon_destroy(struct drm_device *dev, struct nouveau_fbdev *nfbdev) +{ + struct nouveau_framebuffer *nouveau_fb = &nfbdev->nouveau_fb; + struct fb_info *info; + + if (nfbdev->helper.fbdev) { + info = nfbdev->helper.fbdev; + unregister_framebuffer(info); + if (info->cmap.len) + fb_dealloc_cmap(&info->cmap); + framebuffer_release(info); + } + + if (nouveau_fb->nvbo) { + drm_gem_object_unreference_unlocked(nouveau_fb->nvbo->gem); + nouveau_fb->nvbo = NULL; + } + drm_fb_helper_fini(&nfbdev->helper); + drm_framebuffer_cleanup(&nouveau_fb->base); + return 0; +} + +void nouveau_fbcon_gpu_lockup(struct fb_info *info) +{ + struct nouveau_fbdev *nfbdev = info->par; + struct drm_device *dev = nfbdev->dev; + + NV_ERROR(dev, "GPU lockup - switching to software fbcon\n"); + info->flags |= FBINFO_HWACCEL_DISABLED; +} + +static struct drm_fb_helper_funcs nouveau_fbcon_helper_funcs = { + .gamma_set = nouveau_fbcon_gamma_set, + .gamma_get = nouveau_fbcon_gamma_get, + .fb_probe = nouveau_fbcon_find_or_create_single, +}; + + +int nouveau_fbcon_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_fbdev *nfbdev; + int ret; + + nfbdev = kzalloc(sizeof(struct nouveau_fbdev), GFP_KERNEL); + if (!nfbdev) + return -ENOMEM; + + nfbdev->dev = dev; + dev_priv->nfbdev = nfbdev; + nfbdev->helper.funcs = &nouveau_fbcon_helper_funcs; + + ret = drm_fb_helper_init(dev, &nfbdev->helper, + nv_two_heads(dev) ? 2 : 1, 4); + if (ret) { + kfree(nfbdev); + return ret; + } + + drm_fb_helper_single_add_all_connectors(&nfbdev->helper); + drm_fb_helper_initial_config(&nfbdev->helper, 32); + return 0; +} + +void nouveau_fbcon_fini(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + if (!dev_priv->nfbdev) + return; + + nouveau_fbcon_destroy(dev, dev_priv->nfbdev); + kfree(dev_priv->nfbdev); + dev_priv->nfbdev = NULL; +} + +void nouveau_fbcon_save_disable_accel(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + dev_priv->nfbdev->saved_flags = dev_priv->nfbdev->helper.fbdev->flags; + dev_priv->nfbdev->helper.fbdev->flags |= FBINFO_HWACCEL_DISABLED; +} + +void nouveau_fbcon_restore_accel(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + dev_priv->nfbdev->helper.fbdev->flags = dev_priv->nfbdev->saved_flags; +} + +void nouveau_fbcon_set_suspend(struct drm_device *dev, int state) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + fb_set_suspend(dev_priv->nfbdev->helper.fbdev, state); +} + +void nouveau_fbcon_zfill_all(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + nouveau_fbcon_zfill(dev, dev_priv->nfbdev); +} diff --git a/driver/pscnv/nouveau_fbcon.h b/driver/pscnv/nouveau_fbcon.h new file mode 100644 index 00000000..e7e12684 --- /dev/null +++ b/driver/pscnv/nouveau_fbcon.h @@ -0,0 +1,63 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#ifndef __NOUVEAU_FBCON_H__ +#define __NOUVEAU_FBCON_H__ + +#include "drm_fb_helper.h" + +#include "nouveau_fb.h" +struct nouveau_fbdev { + struct drm_fb_helper helper; + struct nouveau_framebuffer nouveau_fb; + struct list_head fbdev_list; + struct drm_device *dev; + unsigned int saved_flags; +}; + +void nouveau_fbcon_restore(void); + +void nv04_fbcon_copyarea(struct fb_info *info, const struct fb_copyarea *region); +void nv04_fbcon_fillrect(struct fb_info *info, const struct fb_fillrect *rect); +void nv04_fbcon_imageblit(struct fb_info *info, const struct fb_image *image); +int nv04_fbcon_accel_init(struct fb_info *info); +void nv50_fbcon_fillrect(struct fb_info *info, const struct fb_fillrect *rect); +void nv50_fbcon_copyarea(struct fb_info *info, const struct fb_copyarea *region); +void nv50_fbcon_imageblit(struct fb_info *info, const struct fb_image *image); +int nv50_fbcon_accel_init(struct fb_info *info); + +void nouveau_fbcon_gpu_lockup(struct fb_info *info); + +int nouveau_fbcon_init(struct drm_device *dev); +void nouveau_fbcon_fini(struct drm_device *dev); +void nouveau_fbcon_set_suspend(struct drm_device *dev, int state); +void nouveau_fbcon_zfill_all(struct drm_device *dev); +void nouveau_fbcon_save_disable_accel(struct drm_device *dev); +void nouveau_fbcon_restore_accel(struct drm_device *dev); + +void nouveau_fbcon_output_poll_changed(struct drm_device *dev); +#endif /* __NV50_FBCON_H__ */ + diff --git a/driver/pscnv/nouveau_grctx.h b/driver/pscnv/nouveau_grctx.h new file mode 100644 index 00000000..d96a86c9 --- /dev/null +++ b/driver/pscnv/nouveau_grctx.h @@ -0,0 +1,136 @@ +#ifndef __NOUVEAU_GRCTX_H__ +#define __NOUVEAU_GRCTX_H__ + +struct nouveau_grctx { + struct drm_device *dev; + + enum { + NOUVEAU_GRCTX_PROG, + NOUVEAU_GRCTX_VALS + } mode; + void *data; + + uint32_t ctxprog_max; + uint32_t ctxprog_len; + uint32_t ctxprog_reg; + int ctxprog_label[32]; + uint32_t ctxvals_pos; + uint32_t ctxvals_base; +}; + +#ifdef CP_CTX +static inline void +cp_out(struct nouveau_grctx *ctx, uint32_t inst) +{ + uint32_t *ctxprog = ctx->data; + + if (ctx->mode != NOUVEAU_GRCTX_PROG) + return; + + BUG_ON(ctx->ctxprog_len == ctx->ctxprog_max); + ctxprog[ctx->ctxprog_len++] = inst; +} + +static inline void +cp_lsr(struct nouveau_grctx *ctx, uint32_t val) +{ + cp_out(ctx, CP_LOAD_SR | val); +} + +static inline void +cp_ctx(struct nouveau_grctx *ctx, uint32_t reg, uint32_t length) +{ + ctx->ctxprog_reg = (reg - 0x00400000) >> 2; + + ctx->ctxvals_base = ctx->ctxvals_pos; + ctx->ctxvals_pos = ctx->ctxvals_base + length; + + if (length > (CP_CTX_COUNT >> CP_CTX_COUNT_SHIFT)) { + cp_lsr(ctx, length); + length = 0; + } + + cp_out(ctx, CP_CTX | (length << CP_CTX_COUNT_SHIFT) | ctx->ctxprog_reg); +} + +static inline void +cp_name(struct nouveau_grctx *ctx, int name) +{ + uint32_t *ctxprog = ctx->data; + int i; + + if (ctx->mode != NOUVEAU_GRCTX_PROG) + return; + + ctx->ctxprog_label[name] = ctx->ctxprog_len; + for (i = 0; i < ctx->ctxprog_len; i++) { + if ((ctxprog[i] & 0xfff00000) != 0xff400000) + continue; + if ((ctxprog[i] & CP_BRA_IP) != ((name) << CP_BRA_IP_SHIFT)) + continue; + ctxprog[i] = (ctxprog[i] & 0x00ff00ff) | + (ctx->ctxprog_len << CP_BRA_IP_SHIFT); + } +} + +static inline void +_cp_bra(struct nouveau_grctx *ctx, u32 mod, int flag, int state, int name) +{ + int ip = 0; + + if (mod != 2) { + ip = ctx->ctxprog_label[name] << CP_BRA_IP_SHIFT; + if (ip == 0) + ip = 0xff000000 | (name << CP_BRA_IP_SHIFT); + } + + cp_out(ctx, CP_BRA | (mod << 18) | ip | flag | + (state ? 0 : CP_BRA_IF_CLEAR)); +} +#define cp_bra(c,f,s,n) _cp_bra((c), 0, CP_FLAG_##f, CP_FLAG_##f##_##s, n) +#ifdef CP_BRA_MOD +#define cp_cal(c,f,s,n) _cp_bra((c), 1, CP_FLAG_##f, CP_FLAG_##f##_##s, n) +#define cp_ret(c,f,s) _cp_bra((c), 2, CP_FLAG_##f, CP_FLAG_##f##_##s, 0) +#endif + +static inline void +_cp_wait(struct nouveau_grctx *ctx, int flag, int state) +{ + cp_out(ctx, CP_WAIT | flag | (state ? CP_WAIT_SET : 0)); +} +#define cp_wait(c,f,s) _cp_wait((c), CP_FLAG_##f, CP_FLAG_##f##_##s) + +static inline void +_cp_set(struct nouveau_grctx *ctx, int flag, int state) +{ + cp_out(ctx, CP_SET | flag | (state ? CP_SET_1 : 0)); +} +#define cp_set(c,f,s) _cp_set((c), CP_FLAG_##f, CP_FLAG_##f##_##s) + +static inline void +cp_pos(struct nouveau_grctx *ctx, int offset) +{ + ctx->ctxvals_pos = offset; + ctx->ctxvals_base = ctx->ctxvals_pos; + + cp_lsr(ctx, ctx->ctxvals_pos); + cp_out(ctx, CP_SET_CONTEXT_POINTER); +} + +static inline void +gr_def(struct nouveau_grctx *ctx, uint32_t reg, uint32_t val) +{ + if (ctx->mode != NOUVEAU_GRCTX_VALS) + return; + + reg = (reg - 0x00400000) / 4; + reg = (reg - ctx->ctxprog_reg) + ctx->ctxvals_base; + + nv_wv32(ctx->data, reg * 4, val); +} +#endif + +extern int +nv50_grctx_init(struct nouveau_grctx *ctx); + +#endif diff --git a/driver/pscnv/nouveau_hw.c b/driver/pscnv/nouveau_hw.c new file mode 100644 index 00000000..5f6610cb --- /dev/null +++ b/driver/pscnv/nouveau_hw.c @@ -0,0 +1,1086 @@ +/* + * Copyright 2006 Dave Airlie + * Copyright 2007 Maarten Maathuis + * Copyright 2007-2009 Stuart Bennett + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF + * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_hw.h" + +#define CHIPSET_NFORCE 0x01a0 +#define CHIPSET_NFORCE2 0x01f0 + +/* + * misc hw access wrappers/control functions + */ + +void +NVWriteVgaSeq(struct drm_device *dev, int head, uint8_t index, uint8_t value) +{ + NVWritePRMVIO(dev, head, NV_PRMVIO_SRX, index); + NVWritePRMVIO(dev, head, NV_PRMVIO_SR, value); +} + +uint8_t +NVReadVgaSeq(struct drm_device *dev, int head, uint8_t index) +{ + NVWritePRMVIO(dev, head, NV_PRMVIO_SRX, index); + return NVReadPRMVIO(dev, head, NV_PRMVIO_SR); +} + +void +NVWriteVgaGr(struct drm_device *dev, int head, uint8_t index, uint8_t value) +{ + NVWritePRMVIO(dev, head, NV_PRMVIO_GRX, index); + NVWritePRMVIO(dev, head, NV_PRMVIO_GX, value); +} + +uint8_t +NVReadVgaGr(struct drm_device *dev, int head, uint8_t index) +{ + NVWritePRMVIO(dev, head, NV_PRMVIO_GRX, index); + return NVReadPRMVIO(dev, head, NV_PRMVIO_GX); +} + +/* CR44 takes values 0 (head A), 3 (head B) and 4 (heads tied) + * it affects only the 8 bit vga io regs, which we access using mmio at + * 0xc{0,2}3c*, 0x60{1,3}3*, and 0x68{1,3}3d* + * in general, the set value of cr44 does not matter: reg access works as + * expected and values can be set for the appropriate head by using a 0x2000 + * offset as required + * however: + * a) pre nv40, the head B range of PRMVIO regs at 0xc23c* was not exposed and + * cr44 must be set to 0 or 3 for accessing values on the correct head + * through the common 0xc03c* addresses + * b) in tied mode (4) head B is programmed to the values set on head A, and + * access using the head B addresses can have strange results, ergo we leave + * tied mode in init once we know to what cr44 should be restored on exit + * + * the owner parameter is slightly abused: + * 0 and 1 are treated as head values and so the set value is (owner * 3) + * other values are treated as literal values to set + */ +void +NVSetOwner(struct drm_device *dev, int owner) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + if (owner == 1) + owner *= 3; + + if (dev_priv->chipset == 0x11) { + /* This might seem stupid, but the blob does it and + * omitting it often locks the system up. + */ + NVReadVgaCrtc(dev, 0, NV_CIO_SR_LOCK_INDEX); + NVReadVgaCrtc(dev, 1, NV_CIO_SR_LOCK_INDEX); + } + + /* CR44 is always changed on CRTC0 */ + NVWriteVgaCrtc(dev, 0, NV_CIO_CRE_44, owner); + + if (dev_priv->chipset == 0x11) { /* set me harder */ + NVWriteVgaCrtc(dev, 0, NV_CIO_CRE_2E, owner); + NVWriteVgaCrtc(dev, 0, NV_CIO_CRE_2E, owner); + } +} + +void +NVBlankScreen(struct drm_device *dev, int head, bool blank) +{ + unsigned char seq1; + + if (nv_two_heads(dev)) + NVSetOwner(dev, head); + + seq1 = NVReadVgaSeq(dev, head, NV_VIO_SR_CLOCK_INDEX); + + NVVgaSeqReset(dev, head, true); + if (blank) + NVWriteVgaSeq(dev, head, NV_VIO_SR_CLOCK_INDEX, seq1 | 0x20); + else + NVWriteVgaSeq(dev, head, NV_VIO_SR_CLOCK_INDEX, seq1 & ~0x20); + NVVgaSeqReset(dev, head, false); +} + +/* + * PLL setting + */ + +static int +powerctrl_1_shift(int chip_version, int reg) +{ + int shift = -4; + + if (chip_version < 0x17 || chip_version == 0x1a || chip_version == 0x20) + return shift; + + switch (reg) { + case NV_RAMDAC_VPLL2: + shift += 4; + case NV_PRAMDAC_VPLL_COEFF: + shift += 4; + case NV_PRAMDAC_MPLL_COEFF: + shift += 4; + case NV_PRAMDAC_NVPLL_COEFF: + shift += 4; + } + + /* + * the shift for vpll regs is only used for nv3x chips with a single + * stage pll + */ + if (shift > 4 && (chip_version < 0x32 || chip_version == 0x35 || + chip_version == 0x36 || chip_version >= 0x40)) + shift = -4; + + return shift; +} + +static void +setPLL_single(struct drm_device *dev, uint32_t reg, struct nouveau_pll_vals *pv) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int chip_version = dev_priv->vbios.chip_version; + uint32_t oldpll = NVReadRAMDAC(dev, 0, reg); + int oldN = (oldpll >> 8) & 0xff, oldM = oldpll & 0xff; + uint32_t pll = (oldpll & 0xfff80000) | pv->log2P << 16 | pv->NM1; + uint32_t saved_powerctrl_1 = 0; + int shift_powerctrl_1 = powerctrl_1_shift(chip_version, reg); + + if (oldpll == pll) + return; /* already set */ + + if (shift_powerctrl_1 >= 0) { + saved_powerctrl_1 = nvReadMC(dev, NV_PBUS_POWERCTRL_1); + nvWriteMC(dev, NV_PBUS_POWERCTRL_1, + (saved_powerctrl_1 & ~(0xf << shift_powerctrl_1)) | + 1 << shift_powerctrl_1); + } + + if (oldM && pv->M1 && (oldN / oldM < pv->N1 / pv->M1)) + /* upclock -- write new post divider first */ + NVWriteRAMDAC(dev, 0, reg, pv->log2P << 16 | (oldpll & 0xffff)); + else + /* downclock -- write new NM first */ + NVWriteRAMDAC(dev, 0, reg, (oldpll & 0xffff0000) | pv->NM1); + + if (chip_version < 0x17 && chip_version != 0x11) + /* wait a bit on older chips */ + msleep(64); + NVReadRAMDAC(dev, 0, reg); + + /* then write the other half as well */ + NVWriteRAMDAC(dev, 0, reg, pll); + + if (shift_powerctrl_1 >= 0) + nvWriteMC(dev, NV_PBUS_POWERCTRL_1, saved_powerctrl_1); +} + +static uint32_t +new_ramdac580(uint32_t reg1, bool ss, uint32_t ramdac580) +{ + bool head_a = (reg1 == NV_PRAMDAC_VPLL_COEFF); + + if (ss) /* single stage pll mode */ + ramdac580 |= head_a ? NV_RAMDAC_580_VPLL1_ACTIVE : + NV_RAMDAC_580_VPLL2_ACTIVE; + else + ramdac580 &= head_a ? ~NV_RAMDAC_580_VPLL1_ACTIVE : + ~NV_RAMDAC_580_VPLL2_ACTIVE; + + return ramdac580; +} + +static void +setPLL_double_highregs(struct drm_device *dev, uint32_t reg1, + struct nouveau_pll_vals *pv) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int chip_version = dev_priv->vbios.chip_version; + bool nv3035 = chip_version == 0x30 || chip_version == 0x35; + uint32_t reg2 = reg1 + ((reg1 == NV_RAMDAC_VPLL2) ? 0x5c : 0x70); + uint32_t oldpll1 = NVReadRAMDAC(dev, 0, reg1); + uint32_t oldpll2 = !nv3035 ? NVReadRAMDAC(dev, 0, reg2) : 0; + uint32_t pll1 = (oldpll1 & 0xfff80000) | pv->log2P << 16 | pv->NM1; + uint32_t pll2 = (oldpll2 & 0x7fff0000) | 1 << 31 | pv->NM2; + uint32_t oldramdac580 = 0, ramdac580 = 0; + bool single_stage = !pv->NM2 || pv->N2 == pv->M2; /* nv41+ only */ + uint32_t saved_powerctrl_1 = 0, savedc040 = 0; + int shift_powerctrl_1 = powerctrl_1_shift(chip_version, reg1); + + /* model specific additions to generic pll1 and pll2 set up above */ + if (nv3035) { + pll1 = (pll1 & 0xfcc7ffff) | (pv->N2 & 0x18) << 21 | + (pv->N2 & 0x7) << 19 | 8 << 4 | (pv->M2 & 7) << 4; + pll2 = 0; + } + if (chip_version > 0x40 && reg1 >= NV_PRAMDAC_VPLL_COEFF) { /* !nv40 */ + oldramdac580 = NVReadRAMDAC(dev, 0, NV_PRAMDAC_580); + ramdac580 = new_ramdac580(reg1, single_stage, oldramdac580); + if (oldramdac580 != ramdac580) + oldpll1 = ~0; /* force mismatch */ + if (single_stage) + /* magic value used by nvidia in single stage mode */ + pll2 |= 0x011f; + } + if (chip_version > 0x70) + /* magic bits set by the blob (but not the bios) on g71-73 */ + pll1 = (pll1 & 0x7fffffff) | (single_stage ? 0x4 : 0xc) << 28; + + if (oldpll1 == pll1 && oldpll2 == pll2) + return; /* already set */ + + if (shift_powerctrl_1 >= 0) { + saved_powerctrl_1 = nvReadMC(dev, NV_PBUS_POWERCTRL_1); + nvWriteMC(dev, NV_PBUS_POWERCTRL_1, + (saved_powerctrl_1 & ~(0xf << shift_powerctrl_1)) | + 1 << shift_powerctrl_1); + } + + if (chip_version >= 0x40) { + int shift_c040 = 14; + + switch (reg1) { + case NV_PRAMDAC_MPLL_COEFF: + shift_c040 += 2; + case NV_PRAMDAC_NVPLL_COEFF: + shift_c040 += 2; + case NV_RAMDAC_VPLL2: + shift_c040 += 2; + case NV_PRAMDAC_VPLL_COEFF: + shift_c040 += 2; + } + + savedc040 = nvReadMC(dev, 0xc040); + if (shift_c040 != 14) + nvWriteMC(dev, 0xc040, savedc040 & ~(3 << shift_c040)); + } + + if (oldramdac580 != ramdac580) + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_580, ramdac580); + + if (!nv3035) + NVWriteRAMDAC(dev, 0, reg2, pll2); + NVWriteRAMDAC(dev, 0, reg1, pll1); + + if (shift_powerctrl_1 >= 0) + nvWriteMC(dev, NV_PBUS_POWERCTRL_1, saved_powerctrl_1); + if (chip_version >= 0x40) + nvWriteMC(dev, 0xc040, savedc040); +} + +static void +setPLL_double_lowregs(struct drm_device *dev, uint32_t NMNMreg, + struct nouveau_pll_vals *pv) +{ + /* When setting PLLs, there is a merry game of disabling and enabling + * various bits of hardware during the process. This function is a + * synthesis of six nv4x traces, nearly each card doing a subtly + * different thing. With luck all the necessary bits for each card are + * combined herein. Without luck it deviates from each card's formula + * so as to not work on any :) + */ + + uint32_t Preg = NMNMreg - 4; + bool mpll = Preg == 0x4020; + uint32_t oldPval = nvReadMC(dev, Preg); + uint32_t NMNM = pv->NM2 << 16 | pv->NM1; + uint32_t Pval = (oldPval & (mpll ? ~(0x77 << 16) : ~(7 << 16))) | + 0xc << 28 | pv->log2P << 16; + uint32_t saved4600 = 0; + /* some cards have different maskc040s */ + uint32_t maskc040 = ~(3 << 14), savedc040; + bool single_stage = !pv->NM2 || pv->N2 == pv->M2; + + if (nvReadMC(dev, NMNMreg) == NMNM && (oldPval & 0xc0070000) == Pval) + return; + + if (Preg == 0x4000) + maskc040 = ~0x333; + if (Preg == 0x4058) + maskc040 = ~(0xc << 24); + + if (mpll) { + struct pll_lims pll_lim; + uint8_t Pval2; + + if (get_pll_limits(dev, Preg, &pll_lim)) + return; + + Pval2 = pv->log2P + pll_lim.log2p_bias; + if (Pval2 > pll_lim.max_log2p) + Pval2 = pll_lim.max_log2p; + Pval |= 1 << 28 | Pval2 << 20; + + saved4600 = nvReadMC(dev, 0x4600); + nvWriteMC(dev, 0x4600, saved4600 | 8 << 28); + } + if (single_stage) + Pval |= mpll ? 1 << 12 : 1 << 8; + + nvWriteMC(dev, Preg, oldPval | 1 << 28); + nvWriteMC(dev, Preg, Pval & ~(4 << 28)); + if (mpll) { + Pval |= 8 << 20; + nvWriteMC(dev, 0x4020, Pval & ~(0xc << 28)); + nvWriteMC(dev, 0x4038, Pval & ~(0xc << 28)); + } + + savedc040 = nvReadMC(dev, 0xc040); + nvWriteMC(dev, 0xc040, savedc040 & maskc040); + + nvWriteMC(dev, NMNMreg, NMNM); + if (NMNMreg == 0x4024) + nvWriteMC(dev, 0x403c, NMNM); + + nvWriteMC(dev, Preg, Pval); + if (mpll) { + Pval &= ~(8 << 20); + nvWriteMC(dev, 0x4020, Pval); + nvWriteMC(dev, 0x4038, Pval); + nvWriteMC(dev, 0x4600, saved4600); + } + + nvWriteMC(dev, 0xc040, savedc040); + + if (mpll) { + nvWriteMC(dev, 0x4020, Pval & ~(1 << 28)); + nvWriteMC(dev, 0x4038, Pval & ~(1 << 28)); + } +} + +void +nouveau_hw_setpll(struct drm_device *dev, uint32_t reg1, + struct nouveau_pll_vals *pv) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int cv = dev_priv->vbios.chip_version; + + if (cv == 0x30 || cv == 0x31 || cv == 0x35 || cv == 0x36 || + cv >= 0x40) { + if (reg1 > 0x405c) + setPLL_double_highregs(dev, reg1, pv); + else + setPLL_double_lowregs(dev, reg1, pv); + } else + setPLL_single(dev, reg1, pv); +} + +/* + * PLL getting + */ + +static void +nouveau_hw_decode_pll(struct drm_device *dev, uint32_t reg1, uint32_t pll1, + uint32_t pll2, struct nouveau_pll_vals *pllvals) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + /* to force parsing as single stage (i.e. nv40 vplls) pass pll2 as 0 */ + + /* log2P is & 0x7 as never more than 7, and nv30/35 only uses 3 bits */ + pllvals->log2P = (pll1 >> 16) & 0x7; + pllvals->N2 = pllvals->M2 = 1; + + if (reg1 <= 0x405c) { + pllvals->NM1 = pll2 & 0xffff; + /* single stage NVPLL and VPLLs use 1 << 8, MPLL uses 1 << 12 */ + if (!(pll1 & 0x1100)) + pllvals->NM2 = pll2 >> 16; + } else { + pllvals->NM1 = pll1 & 0xffff; + if (nv_two_reg_pll(dev) && pll2 & NV31_RAMDAC_ENABLE_VCO2) + pllvals->NM2 = pll2 & 0xffff; + else if (dev_priv->chipset == 0x30 || dev_priv->chipset == 0x35) { + pllvals->M1 &= 0xf; /* only 4 bits */ + if (pll1 & NV30_RAMDAC_ENABLE_VCO2) { + pllvals->M2 = (pll1 >> 4) & 0x7; + pllvals->N2 = ((pll1 >> 21) & 0x18) | + ((pll1 >> 19) & 0x7); + } + } + } +} + +int +nouveau_hw_get_pllvals(struct drm_device *dev, enum pll_types plltype, + struct nouveau_pll_vals *pllvals) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t reg1 = get_pll_register(dev, plltype), pll1, pll2 = 0; + struct pll_lims pll_lim; + int ret; + + if (reg1 == 0) + return -ENOENT; + + pll1 = nvReadMC(dev, reg1); + + if (reg1 <= 0x405c) + pll2 = nvReadMC(dev, reg1 + 4); + else if (nv_two_reg_pll(dev)) { + uint32_t reg2 = reg1 + (reg1 == NV_RAMDAC_VPLL2 ? 0x5c : 0x70); + + pll2 = nvReadMC(dev, reg2); + } + + if (dev_priv->card_type == 0x40 && reg1 >= NV_PRAMDAC_VPLL_COEFF) { + uint32_t ramdac580 = NVReadRAMDAC(dev, 0, NV_PRAMDAC_580); + + /* check whether vpll has been forced into single stage mode */ + if (reg1 == NV_PRAMDAC_VPLL_COEFF) { + if (ramdac580 & NV_RAMDAC_580_VPLL1_ACTIVE) + pll2 = 0; + } else + if (ramdac580 & NV_RAMDAC_580_VPLL2_ACTIVE) + pll2 = 0; + } + + nouveau_hw_decode_pll(dev, reg1, pll1, pll2, pllvals); + + ret = get_pll_limits(dev, plltype, &pll_lim); + if (ret) + return ret; + + pllvals->refclk = pll_lim.refclk; + + return 0; +} + +int +nouveau_hw_pllvals_to_clk(struct nouveau_pll_vals *pv) +{ + /* Avoid divide by zero if called at an inappropriate time */ + if (!pv->M1 || !pv->M2) + return 0; + + return pv->N1 * pv->N2 * pv->refclk / (pv->M1 * pv->M2) >> pv->log2P; +} + +int +nouveau_hw_get_clock(struct drm_device *dev, enum pll_types plltype) +{ + struct nouveau_pll_vals pllvals; + int ret; + + if (plltype == PLL_MEMORY && + (dev->pci_device & 0x0ff0) == CHIPSET_NFORCE) { + uint32_t mpllP; + + pci_read_config_dword(pci_get_bus_and_slot(0, 3), 0x6c, &mpllP); + if (!mpllP) + mpllP = 4; + + return 400000 / mpllP; + } else + if (plltype == PLL_MEMORY && + (dev->pci_device & 0xff0) == CHIPSET_NFORCE2) { + uint32_t clock; + + pci_read_config_dword(pci_get_bus_and_slot(0, 5), 0x4c, &clock); + return clock; + } + + ret = nouveau_hw_get_pllvals(dev, plltype, &pllvals); + if (ret) + return ret; + + return nouveau_hw_pllvals_to_clk(&pllvals); +} + +static void +nouveau_hw_fix_bad_vpll(struct drm_device *dev, int head) +{ + /* the vpll on an unused head can come up with a random value, way + * beyond the pll limits. for some reason this causes the chip to + * lock up when reading the dac palette regs, so set a valid pll here + * when such a condition detected. only seen on nv11 to date + */ + + struct pll_lims pll_lim; + struct nouveau_pll_vals pv; + enum pll_types pll = head ? PLL_VPLL1 : PLL_VPLL0; + + if (get_pll_limits(dev, pll, &pll_lim)) + return; + nouveau_hw_get_pllvals(dev, pll, &pv); + + if (pv.M1 >= pll_lim.vco1.min_m && pv.M1 <= pll_lim.vco1.max_m && + pv.N1 >= pll_lim.vco1.min_n && pv.N1 <= pll_lim.vco1.max_n && + pv.log2P <= pll_lim.max_log2p) + return; + + NV_WARN(dev, "VPLL %d outwith limits, attempting to fix\n", head + 1); + + /* set lowest clock within static limits */ + pv.M1 = pll_lim.vco1.max_m; + pv.N1 = pll_lim.vco1.min_n; + pv.log2P = pll_lim.max_usable_log2p; + nouveau_hw_setpll(dev, pll_lim.reg, &pv); +} + +/* + * vga font save/restore + */ + +static void nouveau_vga_font_io(struct drm_device *dev, + void __iomem *iovram, + bool save, unsigned plane) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + unsigned i; + + NVWriteVgaSeq(dev, 0, NV_VIO_SR_PLANE_MASK_INDEX, 1 << plane); + NVWriteVgaGr(dev, 0, NV_VIO_GX_READ_MAP_INDEX, plane); + for (i = 0; i < 16384; i++) { + if (save) { + dev_priv->saved_vga_font[plane][i] = + ioread32_native(iovram + i * 4); + } else { + iowrite32_native(dev_priv->saved_vga_font[plane][i], + iovram + i * 4); + } + } +} + +void +nouveau_hw_save_vga_fonts(struct drm_device *dev, bool save) +{ + uint8_t misc, gr4, gr5, gr6, seq2, seq4; + bool graphicsmode; + unsigned plane; + void __iomem *iovram; + + if (nv_two_heads(dev)) + NVSetOwner(dev, 0); + + NVSetEnablePalette(dev, 0, true); + graphicsmode = NVReadVgaAttr(dev, 0, NV_CIO_AR_MODE_INDEX) & 1; + NVSetEnablePalette(dev, 0, false); + + if (graphicsmode) /* graphics mode => framebuffer => no need to save */ + return; + + NV_INFO(dev, "%sing VGA fonts\n", save ? "Sav" : "Restor"); + + /* map first 64KiB of VRAM, holds VGA fonts etc */ + iovram = ioremap(pci_resource_start(dev->pdev, 1), 65536); + if (!iovram) { + NV_ERROR(dev, "Failed to map VRAM, " + "cannot save/restore VGA fonts.\n"); + return; + } + + if (nv_two_heads(dev)) + NVBlankScreen(dev, 1, true); + NVBlankScreen(dev, 0, true); + + /* save control regs */ + misc = NVReadPRMVIO(dev, 0, NV_PRMVIO_MISC__READ); + seq2 = NVReadVgaSeq(dev, 0, NV_VIO_SR_PLANE_MASK_INDEX); + seq4 = NVReadVgaSeq(dev, 0, NV_VIO_SR_MEM_MODE_INDEX); + gr4 = NVReadVgaGr(dev, 0, NV_VIO_GX_READ_MAP_INDEX); + gr5 = NVReadVgaGr(dev, 0, NV_VIO_GX_MODE_INDEX); + gr6 = NVReadVgaGr(dev, 0, NV_VIO_GX_MISC_INDEX); + + NVWritePRMVIO(dev, 0, NV_PRMVIO_MISC__WRITE, 0x67); + NVWriteVgaSeq(dev, 0, NV_VIO_SR_MEM_MODE_INDEX, 0x6); + NVWriteVgaGr(dev, 0, NV_VIO_GX_MODE_INDEX, 0x0); + NVWriteVgaGr(dev, 0, NV_VIO_GX_MISC_INDEX, 0x5); + + /* store font in planes 0..3 */ + for (plane = 0; plane < 4; plane++) + nouveau_vga_font_io(dev, iovram, save, plane); + + /* restore control regs */ + NVWritePRMVIO(dev, 0, NV_PRMVIO_MISC__WRITE, misc); + NVWriteVgaGr(dev, 0, NV_VIO_GX_READ_MAP_INDEX, gr4); + NVWriteVgaGr(dev, 0, NV_VIO_GX_MODE_INDEX, gr5); + NVWriteVgaGr(dev, 0, NV_VIO_GX_MISC_INDEX, gr6); + NVWriteVgaSeq(dev, 0, NV_VIO_SR_PLANE_MASK_INDEX, seq2); + NVWriteVgaSeq(dev, 0, NV_VIO_SR_MEM_MODE_INDEX, seq4); + + if (nv_two_heads(dev)) + NVBlankScreen(dev, 1, false); + NVBlankScreen(dev, 0, false); + + iounmap(iovram); +} + +/* + * mode state save/load + */ + +static void +rd_cio_state(struct drm_device *dev, int head, + struct nv04_crtc_reg *crtcstate, int index) +{ + crtcstate->CRTC[index] = NVReadVgaCrtc(dev, head, index); +} + +static void +wr_cio_state(struct drm_device *dev, int head, + struct nv04_crtc_reg *crtcstate, int index) +{ + NVWriteVgaCrtc(dev, head, index, crtcstate->CRTC[index]); +} + +static void +nv_save_state_ramdac(struct drm_device *dev, int head, + struct nv04_mode_state *state) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv04_crtc_reg *regp = &state->crtc_reg[head]; + int i; + + if (dev_priv->card_type >= NV_10) + regp->nv10_cursync = NVReadRAMDAC(dev, head, NV_RAMDAC_NV10_CURSYNC); + + nouveau_hw_get_pllvals(dev, head ? PLL_VPLL1 : PLL_VPLL0, ®p->pllvals); + state->pllsel = NVReadRAMDAC(dev, 0, NV_PRAMDAC_PLL_COEFF_SELECT); + if (nv_two_heads(dev)) + state->sel_clk = NVReadRAMDAC(dev, 0, NV_PRAMDAC_SEL_CLK); + if (dev_priv->chipset == 0x11) + regp->dither = NVReadRAMDAC(dev, head, NV_RAMDAC_DITHER_NV11); + + regp->ramdac_gen_ctrl = NVReadRAMDAC(dev, head, NV_PRAMDAC_GENERAL_CONTROL); + + if (nv_gf4_disp_arch(dev)) + regp->ramdac_630 = NVReadRAMDAC(dev, head, NV_PRAMDAC_630); + if (dev_priv->chipset >= 0x30) + regp->ramdac_634 = NVReadRAMDAC(dev, head, NV_PRAMDAC_634); + + regp->tv_setup = NVReadRAMDAC(dev, head, NV_PRAMDAC_TV_SETUP); + regp->tv_vtotal = NVReadRAMDAC(dev, head, NV_PRAMDAC_TV_VTOTAL); + regp->tv_vskew = NVReadRAMDAC(dev, head, NV_PRAMDAC_TV_VSKEW); + regp->tv_vsync_delay = NVReadRAMDAC(dev, head, NV_PRAMDAC_TV_VSYNC_DELAY); + regp->tv_htotal = NVReadRAMDAC(dev, head, NV_PRAMDAC_TV_HTOTAL); + regp->tv_hskew = NVReadRAMDAC(dev, head, NV_PRAMDAC_TV_HSKEW); + regp->tv_hsync_delay = NVReadRAMDAC(dev, head, NV_PRAMDAC_TV_HSYNC_DELAY); + regp->tv_hsync_delay2 = NVReadRAMDAC(dev, head, NV_PRAMDAC_TV_HSYNC_DELAY2); + + for (i = 0; i < 7; i++) { + uint32_t ramdac_reg = NV_PRAMDAC_FP_VDISPLAY_END + (i * 4); + regp->fp_vert_regs[i] = NVReadRAMDAC(dev, head, ramdac_reg); + regp->fp_horiz_regs[i] = NVReadRAMDAC(dev, head, ramdac_reg + 0x20); + } + + if (nv_gf4_disp_arch(dev)) { + regp->dither = NVReadRAMDAC(dev, head, NV_RAMDAC_FP_DITHER); + for (i = 0; i < 3; i++) { + regp->dither_regs[i] = NVReadRAMDAC(dev, head, NV_PRAMDAC_850 + i * 4); + regp->dither_regs[i + 3] = NVReadRAMDAC(dev, head, NV_PRAMDAC_85C + i * 4); + } + } + + regp->fp_control = NVReadRAMDAC(dev, head, NV_PRAMDAC_FP_TG_CONTROL); + regp->fp_debug_0 = NVReadRAMDAC(dev, head, NV_PRAMDAC_FP_DEBUG_0); + if (!nv_gf4_disp_arch(dev) && head == 0) { + /* early chips don't allow access to PRAMDAC_TMDS_* without + * the head A FPCLK on (nv11 even locks up) */ + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_FP_DEBUG_0, regp->fp_debug_0 & + ~NV_PRAMDAC_FP_DEBUG_0_PWRDOWN_FPCLK); + } + regp->fp_debug_1 = NVReadRAMDAC(dev, head, NV_PRAMDAC_FP_DEBUG_1); + regp->fp_debug_2 = NVReadRAMDAC(dev, head, NV_PRAMDAC_FP_DEBUG_2); + + regp->fp_margin_color = NVReadRAMDAC(dev, head, NV_PRAMDAC_FP_MARGIN_COLOR); + + if (nv_gf4_disp_arch(dev)) + regp->ramdac_8c0 = NVReadRAMDAC(dev, head, NV_PRAMDAC_8C0); + + if (dev_priv->card_type == NV_40) { + regp->ramdac_a20 = NVReadRAMDAC(dev, head, NV_PRAMDAC_A20); + regp->ramdac_a24 = NVReadRAMDAC(dev, head, NV_PRAMDAC_A24); + regp->ramdac_a34 = NVReadRAMDAC(dev, head, NV_PRAMDAC_A34); + + for (i = 0; i < 38; i++) + regp->ctv_regs[i] = NVReadRAMDAC(dev, head, + NV_PRAMDAC_CTV + 4*i); + } +} + +static void +nv_load_state_ramdac(struct drm_device *dev, int head, + struct nv04_mode_state *state) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv04_crtc_reg *regp = &state->crtc_reg[head]; + uint32_t pllreg = head ? NV_RAMDAC_VPLL2 : NV_PRAMDAC_VPLL_COEFF; + int i; + + if (dev_priv->card_type >= NV_10) + NVWriteRAMDAC(dev, head, NV_RAMDAC_NV10_CURSYNC, regp->nv10_cursync); + + nouveau_hw_setpll(dev, pllreg, ®p->pllvals); + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_PLL_COEFF_SELECT, state->pllsel); + if (nv_two_heads(dev)) + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_SEL_CLK, state->sel_clk); + if (dev_priv->chipset == 0x11) + NVWriteRAMDAC(dev, head, NV_RAMDAC_DITHER_NV11, regp->dither); + + NVWriteRAMDAC(dev, head, NV_PRAMDAC_GENERAL_CONTROL, regp->ramdac_gen_ctrl); + + if (nv_gf4_disp_arch(dev)) + NVWriteRAMDAC(dev, head, NV_PRAMDAC_630, regp->ramdac_630); + if (dev_priv->chipset >= 0x30) + NVWriteRAMDAC(dev, head, NV_PRAMDAC_634, regp->ramdac_634); + + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TV_SETUP, regp->tv_setup); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TV_VTOTAL, regp->tv_vtotal); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TV_VSKEW, regp->tv_vskew); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TV_VSYNC_DELAY, regp->tv_vsync_delay); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TV_HTOTAL, regp->tv_htotal); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TV_HSKEW, regp->tv_hskew); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TV_HSYNC_DELAY, regp->tv_hsync_delay); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TV_HSYNC_DELAY2, regp->tv_hsync_delay2); + + for (i = 0; i < 7; i++) { + uint32_t ramdac_reg = NV_PRAMDAC_FP_VDISPLAY_END + (i * 4); + + NVWriteRAMDAC(dev, head, ramdac_reg, regp->fp_vert_regs[i]); + NVWriteRAMDAC(dev, head, ramdac_reg + 0x20, regp->fp_horiz_regs[i]); + } + + if (nv_gf4_disp_arch(dev)) { + NVWriteRAMDAC(dev, head, NV_RAMDAC_FP_DITHER, regp->dither); + for (i = 0; i < 3; i++) { + NVWriteRAMDAC(dev, head, NV_PRAMDAC_850 + i * 4, regp->dither_regs[i]); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_85C + i * 4, regp->dither_regs[i + 3]); + } + } + + NVWriteRAMDAC(dev, head, NV_PRAMDAC_FP_TG_CONTROL, regp->fp_control); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_FP_DEBUG_0, regp->fp_debug_0); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_FP_DEBUG_1, regp->fp_debug_1); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_FP_DEBUG_2, regp->fp_debug_2); + + NVWriteRAMDAC(dev, head, NV_PRAMDAC_FP_MARGIN_COLOR, regp->fp_margin_color); + + if (nv_gf4_disp_arch(dev)) + NVWriteRAMDAC(dev, head, NV_PRAMDAC_8C0, regp->ramdac_8c0); + + if (dev_priv->card_type == NV_40) { + NVWriteRAMDAC(dev, head, NV_PRAMDAC_A20, regp->ramdac_a20); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_A24, regp->ramdac_a24); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_A34, regp->ramdac_a34); + + for (i = 0; i < 38; i++) + NVWriteRAMDAC(dev, head, + NV_PRAMDAC_CTV + 4*i, regp->ctv_regs[i]); + } +} + +static void +nv_save_state_vga(struct drm_device *dev, int head, + struct nv04_mode_state *state) +{ + struct nv04_crtc_reg *regp = &state->crtc_reg[head]; + int i; + + regp->MiscOutReg = NVReadPRMVIO(dev, head, NV_PRMVIO_MISC__READ); + + for (i = 0; i < 25; i++) + rd_cio_state(dev, head, regp, i); + + NVSetEnablePalette(dev, head, true); + for (i = 0; i < 21; i++) + regp->Attribute[i] = NVReadVgaAttr(dev, head, i); + NVSetEnablePalette(dev, head, false); + + for (i = 0; i < 9; i++) + regp->Graphics[i] = NVReadVgaGr(dev, head, i); + + for (i = 0; i < 5; i++) + regp->Sequencer[i] = NVReadVgaSeq(dev, head, i); +} + +static void +nv_load_state_vga(struct drm_device *dev, int head, + struct nv04_mode_state *state) +{ + struct nv04_crtc_reg *regp = &state->crtc_reg[head]; + int i; + + NVWritePRMVIO(dev, head, NV_PRMVIO_MISC__WRITE, regp->MiscOutReg); + + for (i = 0; i < 5; i++) + NVWriteVgaSeq(dev, head, i, regp->Sequencer[i]); + + nv_lock_vga_crtc_base(dev, head, false); + for (i = 0; i < 25; i++) + wr_cio_state(dev, head, regp, i); + nv_lock_vga_crtc_base(dev, head, true); + + for (i = 0; i < 9; i++) + NVWriteVgaGr(dev, head, i, regp->Graphics[i]); + + NVSetEnablePalette(dev, head, true); + for (i = 0; i < 21; i++) + NVWriteVgaAttr(dev, head, i, regp->Attribute[i]); + NVSetEnablePalette(dev, head, false); +} + +static void +nv_save_state_ext(struct drm_device *dev, int head, + struct nv04_mode_state *state) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv04_crtc_reg *regp = &state->crtc_reg[head]; + int i; + + rd_cio_state(dev, head, regp, NV_CIO_CRE_LCD__INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_RPC0_INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_RPC1_INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_LSR_INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_PIXEL_INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_HEB__INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_ENH_INDEX); + + rd_cio_state(dev, head, regp, NV_CIO_CRE_FF_INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_FFLWM__INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_21); + + if (dev_priv->card_type >= NV_20) + rd_cio_state(dev, head, regp, NV_CIO_CRE_47); + + if (dev_priv->card_type >= NV_30) + rd_cio_state(dev, head, regp, 0x9f); + + rd_cio_state(dev, head, regp, NV_CIO_CRE_49); + rd_cio_state(dev, head, regp, NV_CIO_CRE_HCUR_ADDR0_INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_HCUR_ADDR1_INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_HCUR_ADDR2_INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_ILACE__INDEX); + + if (dev_priv->card_type >= NV_10) { + regp->crtc_830 = NVReadCRTC(dev, head, NV_PCRTC_830); + regp->crtc_834 = NVReadCRTC(dev, head, NV_PCRTC_834); + + if (dev_priv->card_type >= NV_30) + regp->gpio_ext = NVReadCRTC(dev, head, NV_PCRTC_GPIO_EXT); + + if (dev_priv->card_type == NV_40) + regp->crtc_850 = NVReadCRTC(dev, head, NV_PCRTC_850); + + if (nv_two_heads(dev)) + regp->crtc_eng_ctrl = NVReadCRTC(dev, head, NV_PCRTC_ENGINE_CTRL); + regp->cursor_cfg = NVReadCRTC(dev, head, NV_PCRTC_CURSOR_CONFIG); + } + + regp->crtc_cfg = NVReadCRTC(dev, head, NV_PCRTC_CONFIG); + + rd_cio_state(dev, head, regp, NV_CIO_CRE_SCRATCH3__INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_SCRATCH4__INDEX); + if (dev_priv->card_type >= NV_10) { + rd_cio_state(dev, head, regp, NV_CIO_CRE_EBR_INDEX); + rd_cio_state(dev, head, regp, NV_CIO_CRE_CSB); + rd_cio_state(dev, head, regp, NV_CIO_CRE_4B); + rd_cio_state(dev, head, regp, NV_CIO_CRE_TVOUT_LATENCY); + } + /* NV11 and NV20 don't have this, they stop at 0x52. */ + if (nv_gf4_disp_arch(dev)) { + rd_cio_state(dev, head, regp, NV_CIO_CRE_53); + rd_cio_state(dev, head, regp, NV_CIO_CRE_54); + + for (i = 0; i < 0x10; i++) + regp->CR58[i] = NVReadVgaCrtc5758(dev, head, i); + rd_cio_state(dev, head, regp, NV_CIO_CRE_59); + rd_cio_state(dev, head, regp, NV_CIO_CRE_5B); + + rd_cio_state(dev, head, regp, NV_CIO_CRE_85); + rd_cio_state(dev, head, regp, NV_CIO_CRE_86); + } + + regp->fb_start = NVReadCRTC(dev, head, NV_PCRTC_START); +} + +static void +nv_load_state_ext(struct drm_device *dev, int head, + struct nv04_mode_state *state) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv04_crtc_reg *regp = &state->crtc_reg[head]; + uint32_t reg900; + int i; + + if (dev_priv->card_type >= NV_10) { + if (nv_two_heads(dev)) + /* setting ENGINE_CTRL (EC) *must* come before + * CIO_CRE_LCD, as writing CRE_LCD sets bits 16 & 17 in + * EC that should not be overwritten by writing stale EC + */ + NVWriteCRTC(dev, head, NV_PCRTC_ENGINE_CTRL, regp->crtc_eng_ctrl); + + nvWriteVIDEO(dev, NV_PVIDEO_STOP, 1); + nvWriteVIDEO(dev, NV_PVIDEO_INTR_EN, 0); + nvWriteVIDEO(dev, NV_PVIDEO_OFFSET_BUFF(0), 0); + nvWriteVIDEO(dev, NV_PVIDEO_OFFSET_BUFF(1), 0); +#if 0 + nvWriteVIDEO(dev, NV_PVIDEO_LIMIT(0), dev_priv->fb_available_size - 1); + nvWriteVIDEO(dev, NV_PVIDEO_LIMIT(1), dev_priv->fb_available_size - 1); + nvWriteVIDEO(dev, NV_PVIDEO_UVPLANE_LIMIT(0), dev_priv->fb_available_size - 1); + nvWriteVIDEO(dev, NV_PVIDEO_UVPLANE_LIMIT(1), dev_priv->fb_available_size - 1); +#endif + nvWriteMC(dev, NV_PBUS_POWERCTRL_2, 0); + + NVWriteCRTC(dev, head, NV_PCRTC_CURSOR_CONFIG, regp->cursor_cfg); + NVWriteCRTC(dev, head, NV_PCRTC_830, regp->crtc_830); + NVWriteCRTC(dev, head, NV_PCRTC_834, regp->crtc_834); + + if (dev_priv->card_type >= NV_30) + NVWriteCRTC(dev, head, NV_PCRTC_GPIO_EXT, regp->gpio_ext); + + if (dev_priv->card_type == NV_40) { + NVWriteCRTC(dev, head, NV_PCRTC_850, regp->crtc_850); + + reg900 = NVReadRAMDAC(dev, head, NV_PRAMDAC_900); + if (regp->crtc_cfg == NV_PCRTC_CONFIG_START_ADDRESS_HSYNC) + NVWriteRAMDAC(dev, head, NV_PRAMDAC_900, reg900 | 0x10000); + else + NVWriteRAMDAC(dev, head, NV_PRAMDAC_900, reg900 & ~0x10000); + } + } + + NVWriteCRTC(dev, head, NV_PCRTC_CONFIG, regp->crtc_cfg); + + wr_cio_state(dev, head, regp, NV_CIO_CRE_RPC0_INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_RPC1_INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_LSR_INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_PIXEL_INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_LCD__INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_HEB__INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_ENH_INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_FF_INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_FFLWM__INDEX); + + if (dev_priv->card_type >= NV_20) + wr_cio_state(dev, head, regp, NV_CIO_CRE_47); + + if (dev_priv->card_type >= NV_30) + wr_cio_state(dev, head, regp, 0x9f); + + wr_cio_state(dev, head, regp, NV_CIO_CRE_49); + wr_cio_state(dev, head, regp, NV_CIO_CRE_HCUR_ADDR0_INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_HCUR_ADDR1_INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_HCUR_ADDR2_INDEX); + if (dev_priv->card_type == NV_40) + nv_fix_nv40_hw_cursor(dev, head); + wr_cio_state(dev, head, regp, NV_CIO_CRE_ILACE__INDEX); + + wr_cio_state(dev, head, regp, NV_CIO_CRE_SCRATCH3__INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_SCRATCH4__INDEX); + if (dev_priv->card_type >= NV_10) { + wr_cio_state(dev, head, regp, NV_CIO_CRE_EBR_INDEX); + wr_cio_state(dev, head, regp, NV_CIO_CRE_CSB); + wr_cio_state(dev, head, regp, NV_CIO_CRE_4B); + wr_cio_state(dev, head, regp, NV_CIO_CRE_TVOUT_LATENCY); + } + /* NV11 and NV20 stop at 0x52. */ + if (nv_gf4_disp_arch(dev)) { + if (dev_priv->card_type == NV_10) { + /* Not waiting for vertical retrace before modifying + CRE_53/CRE_54 causes lockups. */ + nouveau_wait_until(dev, 650000000, NV_PRMCIO_INP0__COLOR, 0x8, 0x8); + nouveau_wait_until(dev, 650000000, NV_PRMCIO_INP0__COLOR, 0x8, 0x0); + } + + wr_cio_state(dev, head, regp, NV_CIO_CRE_53); + wr_cio_state(dev, head, regp, NV_CIO_CRE_54); + + for (i = 0; i < 0x10; i++) + NVWriteVgaCrtc5758(dev, head, i, regp->CR58[i]); + wr_cio_state(dev, head, regp, NV_CIO_CRE_59); + wr_cio_state(dev, head, regp, NV_CIO_CRE_5B); + + wr_cio_state(dev, head, regp, NV_CIO_CRE_85); + wr_cio_state(dev, head, regp, NV_CIO_CRE_86); + } + + NVWriteCRTC(dev, head, NV_PCRTC_START, regp->fb_start); + + /* Setting 1 on this value gives you interrupts for every vblank period. */ + NVWriteCRTC(dev, head, NV_PCRTC_INTR_EN_0, 0); + NVWriteCRTC(dev, head, NV_PCRTC_INTR_0, NV_PCRTC_INTR_0_VBLANK); +} + +static void +nv_save_state_palette(struct drm_device *dev, int head, + struct nv04_mode_state *state) +{ + int head_offset = head * NV_PRMDIO_SIZE, i; + + nv_wr08(dev, NV_PRMDIO_PIXEL_MASK + head_offset, + NV_PRMDIO_PIXEL_MASK_MASK); + nv_wr08(dev, NV_PRMDIO_READ_MODE_ADDRESS + head_offset, 0x0); + + for (i = 0; i < 768; i++) { + state->crtc_reg[head].DAC[i] = nv_rd08(dev, + NV_PRMDIO_PALETTE_DATA + head_offset); + } + + NVSetEnablePalette(dev, head, false); +} + +void +nouveau_hw_load_state_palette(struct drm_device *dev, int head, + struct nv04_mode_state *state) +{ + int head_offset = head * NV_PRMDIO_SIZE, i; + + nv_wr08(dev, NV_PRMDIO_PIXEL_MASK + head_offset, + NV_PRMDIO_PIXEL_MASK_MASK); + nv_wr08(dev, NV_PRMDIO_WRITE_MODE_ADDRESS + head_offset, 0x0); + + for (i = 0; i < 768; i++) { + nv_wr08(dev, NV_PRMDIO_PALETTE_DATA + head_offset, + state->crtc_reg[head].DAC[i]); + } + + NVSetEnablePalette(dev, head, false); +} + +void nouveau_hw_save_state(struct drm_device *dev, int head, + struct nv04_mode_state *state) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + if (dev_priv->chipset == 0x11) + /* NB: no attempt is made to restore the bad pll later on */ + nouveau_hw_fix_bad_vpll(dev, head); + nv_save_state_ramdac(dev, head, state); + nv_save_state_vga(dev, head, state); + nv_save_state_palette(dev, head, state); + nv_save_state_ext(dev, head, state); +} + +void nouveau_hw_load_state(struct drm_device *dev, int head, + struct nv04_mode_state *state) +{ + NVVgaProtect(dev, head, true); + nv_load_state_ramdac(dev, head, state); + nv_load_state_ext(dev, head, state); + nouveau_hw_load_state_palette(dev, head, state); + nv_load_state_vga(dev, head, state); + NVVgaProtect(dev, head, false); +} diff --git a/driver/pscnv/nouveau_hw.h b/driver/pscnv/nouveau_hw.h new file mode 100644 index 00000000..869130f8 --- /dev/null +++ b/driver/pscnv/nouveau_hw.h @@ -0,0 +1,455 @@ +/* + * Copyright 2008 Stuart Bennett + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF + * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +#ifndef __NOUVEAU_HW_H__ +#define __NOUVEAU_HW_H__ + +#include "drmP.h" +#include "nouveau_drv.h" + +#define MASK(field) ( \ + (0xffffffff >> (31 - ((1 ? field) - (0 ? field)))) << (0 ? field)) + +#define XLATE(src, srclowbit, outfield) ( \ + (((src) >> (srclowbit)) << (0 ? outfield)) & MASK(outfield)) + +void NVWriteVgaSeq(struct drm_device *, int head, uint8_t index, uint8_t value); +uint8_t NVReadVgaSeq(struct drm_device *, int head, uint8_t index); +void NVWriteVgaGr(struct drm_device *, int head, uint8_t index, uint8_t value); +uint8_t NVReadVgaGr(struct drm_device *, int head, uint8_t index); +void NVSetOwner(struct drm_device *, int owner); +void NVBlankScreen(struct drm_device *, int head, bool blank); +void nouveau_hw_setpll(struct drm_device *, uint32_t reg1, + struct nouveau_pll_vals *pv); +int nouveau_hw_get_pllvals(struct drm_device *, enum pll_types plltype, + struct nouveau_pll_vals *pllvals); +int nouveau_hw_pllvals_to_clk(struct nouveau_pll_vals *pllvals); +int nouveau_hw_get_clock(struct drm_device *, enum pll_types plltype); +void nouveau_hw_save_vga_fonts(struct drm_device *, bool save); +void nouveau_hw_save_state(struct drm_device *, int head, + struct nv04_mode_state *state); +void nouveau_hw_load_state(struct drm_device *, int head, + struct nv04_mode_state *state); +void nouveau_hw_load_state_palette(struct drm_device *, int head, + struct nv04_mode_state *state); + +/* nouveau_calc.c */ +extern void nouveau_calc_arb(struct drm_device *, int vclk, int bpp, + int *burst, int *lwm); +extern int nouveau_calc_pll_mnp(struct drm_device *, struct pll_lims *pll_lim, + int clk, struct nouveau_pll_vals *pv); + +static inline uint32_t +nvReadMC(struct drm_device *dev, uint32_t reg) +{ + uint32_t val = nv_rd32(dev, reg); + NV_REG_DEBUG(MC, dev, "reg %08x val %08x\n", reg, val); + return val; +} + +static inline void +nvWriteMC(struct drm_device *dev, uint32_t reg, uint32_t val) +{ + NV_REG_DEBUG(MC, dev, "reg %08x val %08x\n", reg, val); + nv_wr32(dev, reg, val); +} + +static inline uint32_t +nvReadVIDEO(struct drm_device *dev, uint32_t reg) +{ + uint32_t val = nv_rd32(dev, reg); + NV_REG_DEBUG(VIDEO, dev, "reg %08x val %08x\n", reg, val); + return val; +} + +static inline void +nvWriteVIDEO(struct drm_device *dev, uint32_t reg, uint32_t val) +{ + NV_REG_DEBUG(VIDEO, dev, "reg %08x val %08x\n", reg, val); + nv_wr32(dev, reg, val); +} + +static inline uint32_t +nvReadFB(struct drm_device *dev, uint32_t reg) +{ + uint32_t val = nv_rd32(dev, reg); + NV_REG_DEBUG(FB, dev, "reg %08x val %08x\n", reg, val); + return val; +} + +static inline void +nvWriteFB(struct drm_device *dev, uint32_t reg, uint32_t val) +{ + NV_REG_DEBUG(FB, dev, "reg %08x val %08x\n", reg, val); + nv_wr32(dev, reg, val); +} + +static inline uint32_t +nvReadEXTDEV(struct drm_device *dev, uint32_t reg) +{ + uint32_t val = nv_rd32(dev, reg); + NV_REG_DEBUG(EXTDEV, dev, "reg %08x val %08x\n", reg, val); + return val; +} + +static inline void +nvWriteEXTDEV(struct drm_device *dev, uint32_t reg, uint32_t val) +{ + NV_REG_DEBUG(EXTDEV, dev, "reg %08x val %08x\n", reg, val); + nv_wr32(dev, reg, val); +} + +static inline uint32_t NVReadCRTC(struct drm_device *dev, + int head, uint32_t reg) +{ + uint32_t val; + if (head) + reg += NV_PCRTC0_SIZE; + val = nv_rd32(dev, reg); + NV_REG_DEBUG(CRTC, dev, "head %d reg %08x val %08x\n", head, reg, val); + return val; +} + +static inline void NVWriteCRTC(struct drm_device *dev, + int head, uint32_t reg, uint32_t val) +{ + if (head) + reg += NV_PCRTC0_SIZE; + NV_REG_DEBUG(CRTC, dev, "head %d reg %08x val %08x\n", head, reg, val); + nv_wr32(dev, reg, val); +} + +static inline uint32_t NVReadRAMDAC(struct drm_device *dev, + int head, uint32_t reg) +{ + uint32_t val; + if (head) + reg += NV_PRAMDAC0_SIZE; + val = nv_rd32(dev, reg); + NV_REG_DEBUG(RAMDAC, dev, "head %d reg %08x val %08x\n", + head, reg, val); + return val; +} + +static inline void NVWriteRAMDAC(struct drm_device *dev, + int head, uint32_t reg, uint32_t val) +{ + if (head) + reg += NV_PRAMDAC0_SIZE; + NV_REG_DEBUG(RAMDAC, dev, "head %d reg %08x val %08x\n", + head, reg, val); + nv_wr32(dev, reg, val); +} + +static inline uint8_t nv_read_tmds(struct drm_device *dev, + int or, int dl, uint8_t address) +{ + int ramdac = (or & OUTPUT_C) >> 2; + + NVWriteRAMDAC(dev, ramdac, NV_PRAMDAC_FP_TMDS_CONTROL + dl * 8, + NV_PRAMDAC_FP_TMDS_CONTROL_WRITE_DISABLE | address); + return NVReadRAMDAC(dev, ramdac, NV_PRAMDAC_FP_TMDS_DATA + dl * 8); +} + +static inline void nv_write_tmds(struct drm_device *dev, + int or, int dl, uint8_t address, + uint8_t data) +{ + int ramdac = (or & OUTPUT_C) >> 2; + + NVWriteRAMDAC(dev, ramdac, NV_PRAMDAC_FP_TMDS_DATA + dl * 8, data); + NVWriteRAMDAC(dev, ramdac, NV_PRAMDAC_FP_TMDS_CONTROL + dl * 8, address); +} + +static inline void NVWriteVgaCrtc(struct drm_device *dev, + int head, uint8_t index, uint8_t value) +{ + NV_REG_DEBUG(VGACRTC, dev, "head %d index 0x%02x data 0x%02x\n", + head, index, value); + nv_wr08(dev, NV_PRMCIO_CRX__COLOR + head * NV_PRMCIO_SIZE, index); + nv_wr08(dev, NV_PRMCIO_CR__COLOR + head * NV_PRMCIO_SIZE, value); +} + +static inline uint8_t NVReadVgaCrtc(struct drm_device *dev, + int head, uint8_t index) +{ + uint8_t val; + nv_wr08(dev, NV_PRMCIO_CRX__COLOR + head * NV_PRMCIO_SIZE, index); + val = nv_rd08(dev, NV_PRMCIO_CR__COLOR + head * NV_PRMCIO_SIZE); + NV_REG_DEBUG(VGACRTC, dev, "head %d index 0x%02x data 0x%02x\n", + head, index, val); + return val; +} + +/* CR57 and CR58 are a fun pair of regs. CR57 provides an index (0-0xf) for CR58 + * I suspect they in fact do nothing, but are merely a way to carry useful + * per-head variables around + * + * Known uses: + * CR57 CR58 + * 0x00 index to the appropriate dcb entry (or 7f for inactive) + * 0x02 dcb entry's "or" value (or 00 for inactive) + * 0x03 bit0 set for dual link (LVDS, possibly elsewhere too) + * 0x08 or 0x09 pxclk in MHz + * 0x0f laptop panel info - low nibble for PEXTDEV_BOOT_0 strap + * high nibble for xlat strap value + */ + +static inline void +NVWriteVgaCrtc5758(struct drm_device *dev, int head, uint8_t index, uint8_t value) +{ + NVWriteVgaCrtc(dev, head, NV_CIO_CRE_57, index); + NVWriteVgaCrtc(dev, head, NV_CIO_CRE_58, value); +} + +static inline uint8_t NVReadVgaCrtc5758(struct drm_device *dev, int head, uint8_t index) +{ + NVWriteVgaCrtc(dev, head, NV_CIO_CRE_57, index); + return NVReadVgaCrtc(dev, head, NV_CIO_CRE_58); +} + +static inline uint8_t NVReadPRMVIO(struct drm_device *dev, + int head, uint32_t reg) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint8_t val; + + /* Only NV4x have two pvio ranges; other twoHeads cards MUST call + * NVSetOwner for the relevant head to be programmed */ + if (head && dev_priv->card_type == NV_40) + reg += NV_PRMVIO_SIZE; + + val = nv_rd08(dev, reg); + NV_REG_DEBUG(RMVIO, dev, "head %d reg %08x val %02x\n", head, reg, val); + return val; +} + +static inline void NVWritePRMVIO(struct drm_device *dev, + int head, uint32_t reg, uint8_t value) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + /* Only NV4x have two pvio ranges; other twoHeads cards MUST call + * NVSetOwner for the relevant head to be programmed */ + if (head && dev_priv->card_type == NV_40) + reg += NV_PRMVIO_SIZE; + + NV_REG_DEBUG(RMVIO, dev, "head %d reg %08x val %02x\n", + head, reg, value); + nv_wr08(dev, reg, value); +} + +static inline void NVSetEnablePalette(struct drm_device *dev, int head, bool enable) +{ + nv_rd08(dev, NV_PRMCIO_INP0__COLOR + head * NV_PRMCIO_SIZE); + nv_wr08(dev, NV_PRMCIO_ARX + head * NV_PRMCIO_SIZE, enable ? 0 : 0x20); +} + +static inline bool NVGetEnablePalette(struct drm_device *dev, int head) +{ + nv_rd08(dev, NV_PRMCIO_INP0__COLOR + head * NV_PRMCIO_SIZE); + return !(nv_rd08(dev, NV_PRMCIO_ARX + head * NV_PRMCIO_SIZE) & 0x20); +} + +static inline void NVWriteVgaAttr(struct drm_device *dev, + int head, uint8_t index, uint8_t value) +{ + if (NVGetEnablePalette(dev, head)) + index &= ~0x20; + else + index |= 0x20; + + nv_rd08(dev, NV_PRMCIO_INP0__COLOR + head * NV_PRMCIO_SIZE); + NV_REG_DEBUG(VGAATTR, dev, "head %d index 0x%02x data 0x%02x\n", + head, index, value); + nv_wr08(dev, NV_PRMCIO_ARX + head * NV_PRMCIO_SIZE, index); + nv_wr08(dev, NV_PRMCIO_AR__WRITE + head * NV_PRMCIO_SIZE, value); +} + +static inline uint8_t NVReadVgaAttr(struct drm_device *dev, + int head, uint8_t index) +{ + uint8_t val; + if (NVGetEnablePalette(dev, head)) + index &= ~0x20; + else + index |= 0x20; + + nv_rd08(dev, NV_PRMCIO_INP0__COLOR + head * NV_PRMCIO_SIZE); + nv_wr08(dev, NV_PRMCIO_ARX + head * NV_PRMCIO_SIZE, index); + val = nv_rd08(dev, NV_PRMCIO_AR__READ + head * NV_PRMCIO_SIZE); + NV_REG_DEBUG(VGAATTR, dev, "head %d index 0x%02x data 0x%02x\n", + head, index, val); + return val; +} + +static inline void NVVgaSeqReset(struct drm_device *dev, int head, bool start) +{ + NVWriteVgaSeq(dev, head, NV_VIO_SR_RESET_INDEX, start ? 0x1 : 0x3); +} + +static inline void NVVgaProtect(struct drm_device *dev, int head, bool protect) +{ + uint8_t seq1 = NVReadVgaSeq(dev, head, NV_VIO_SR_CLOCK_INDEX); + + if (protect) { + NVVgaSeqReset(dev, head, true); + NVWriteVgaSeq(dev, head, NV_VIO_SR_CLOCK_INDEX, seq1 | 0x20); + } else { + /* Reenable sequencer, then turn on screen */ + NVWriteVgaSeq(dev, head, NV_VIO_SR_CLOCK_INDEX, seq1 & ~0x20); /* reenable display */ + NVVgaSeqReset(dev, head, false); + } + NVSetEnablePalette(dev, head, protect); +} + +static inline bool +nv_heads_tied(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + if (dev_priv->chipset == 0x11) + return !!(nvReadMC(dev, NV_PBUS_DEBUG_1) & (1 << 28)); + + return NVReadVgaCrtc(dev, 0, NV_CIO_CRE_44) & 0x4; +} + +/* makes cr0-7 on the specified head read-only */ +static inline bool +nv_lock_vga_crtc_base(struct drm_device *dev, int head, bool lock) +{ + uint8_t cr11 = NVReadVgaCrtc(dev, head, NV_CIO_CR_VRE_INDEX); + bool waslocked = cr11 & 0x80; + + if (lock) + cr11 |= 0x80; + else + cr11 &= ~0x80; + NVWriteVgaCrtc(dev, head, NV_CIO_CR_VRE_INDEX, cr11); + + return waslocked; +} + +static inline void +nv_lock_vga_crtc_shadow(struct drm_device *dev, int head, int lock) +{ + /* shadow lock: connects 0x60?3d? regs to "real" 0x3d? regs + * bit7: unlocks HDT, HBS, HBE, HRS, HRE, HEB + * bit6: seems to have some effect on CR09 (double scan, VBS_9) + * bit5: unlocks HDE + * bit4: unlocks VDE + * bit3: unlocks VDT, OVL, VRS, ?VRE?, VBS, VBE, LSR, EBR + * bit2: same as bit 1 of 0x60?804 + * bit0: same as bit 0 of 0x60?804 + */ + + uint8_t cr21 = lock; + + if (lock < 0) + /* 0xfa is generic "unlock all" mask */ + cr21 = NVReadVgaCrtc(dev, head, NV_CIO_CRE_21) | 0xfa; + + NVWriteVgaCrtc(dev, head, NV_CIO_CRE_21, cr21); +} + +/* renders the extended crtc regs (cr19+) on all crtcs impervious: + * immutable and unreadable + */ +static inline bool +NVLockVgaCrtcs(struct drm_device *dev, bool lock) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + bool waslocked = !NVReadVgaCrtc(dev, 0, NV_CIO_SR_LOCK_INDEX); + + NVWriteVgaCrtc(dev, 0, NV_CIO_SR_LOCK_INDEX, + lock ? NV_CIO_SR_LOCK_VALUE : NV_CIO_SR_UNLOCK_RW_VALUE); + /* NV11 has independently lockable extended crtcs, except when tied */ + if (dev_priv->chipset == 0x11 && !nv_heads_tied(dev)) + NVWriteVgaCrtc(dev, 1, NV_CIO_SR_LOCK_INDEX, + lock ? NV_CIO_SR_LOCK_VALUE : + NV_CIO_SR_UNLOCK_RW_VALUE); + + return waslocked; +} + +/* nv04 cursor max dimensions of 32x32 (A1R5G5B5) */ +#define NV04_CURSOR_SIZE 32 +/* limit nv10 cursors to 64x64 (ARGB8) (we could go to 64x255) */ +#define NV10_CURSOR_SIZE 64 + +static inline int nv_cursor_width(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + return dev_priv->card_type >= NV_10 ? NV10_CURSOR_SIZE : NV04_CURSOR_SIZE; +} + +static inline void +nv_fix_nv40_hw_cursor(struct drm_device *dev, int head) +{ + /* on some nv40 (such as the "true" (in the NV_PFB_BOOT_0 sense) nv40, + * the gf6800gt) a hardware bug requires a write to PRAMDAC_CURSOR_POS + * for changes to the CRTC CURCTL regs to take effect, whether changing + * the pixmap location, or just showing/hiding the cursor + */ + uint32_t curpos = NVReadRAMDAC(dev, head, NV_PRAMDAC_CU_START_POS); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_CU_START_POS, curpos); +} + +static inline void +nv_show_cursor(struct drm_device *dev, int head, bool show) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint8_t *curctl1 = + &dev_priv->mode_reg.crtc_reg[head].CRTC[NV_CIO_CRE_HCUR_ADDR1_INDEX]; + + if (show) + *curctl1 |= MASK(NV_CIO_CRE_HCUR_ADDR1_ENABLE); + else + *curctl1 &= ~MASK(NV_CIO_CRE_HCUR_ADDR1_ENABLE); + NVWriteVgaCrtc(dev, head, NV_CIO_CRE_HCUR_ADDR1_INDEX, *curctl1); + + if (dev_priv->card_type == NV_40) + nv_fix_nv40_hw_cursor(dev, head); +} + +static inline uint32_t +nv_pitch_align(struct drm_device *dev, uint32_t width, int bpp) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int mask; + + if (bpp == 15) + bpp = 16; + if (bpp == 24) + bpp = 8; + + /* Alignment requirements taken from the Haiku driver */ + if (dev_priv->card_type == NV_04) + mask = 128 / bpp - 1; + else + mask = 512 / bpp - 1; + + return (width + mask) & ~mask; +} + +#endif /* __NOUVEAU_HW_H__ */ diff --git a/driver/pscnv/nouveau_i2c.c b/driver/pscnv/nouveau_i2c.c new file mode 100644 index 00000000..fdd7e3de --- /dev/null +++ b/driver/pscnv/nouveau_i2c.c @@ -0,0 +1,323 @@ +/* + * Copyright 2009 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_i2c.h" +#include "nouveau_hw.h" + +static void +nv04_i2c_setscl(void *data, int state) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + uint8_t val; + + val = (NVReadVgaCrtc(dev, 0, i2c->wr) & 0xd0) | (state ? 0x20 : 0); + NVWriteVgaCrtc(dev, 0, i2c->wr, val | 0x01); +} + +static void +nv04_i2c_setsda(void *data, int state) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + uint8_t val; + + val = (NVReadVgaCrtc(dev, 0, i2c->wr) & 0xe0) | (state ? 0x10 : 0); + NVWriteVgaCrtc(dev, 0, i2c->wr, val | 0x01); +} + +static int +nv04_i2c_getscl(void *data) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + + return !!(NVReadVgaCrtc(dev, 0, i2c->rd) & 4); +} + +static int +nv04_i2c_getsda(void *data) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + + return !!(NVReadVgaCrtc(dev, 0, i2c->rd) & 8); +} + +static void +nv4e_i2c_setscl(void *data, int state) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + uint8_t val; + + val = (nv_rd32(dev, i2c->wr) & 0xd0) | (state ? 0x20 : 0); + nv_wr32(dev, i2c->wr, val | 0x01); +} + +static void +nv4e_i2c_setsda(void *data, int state) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + uint8_t val; + + val = (nv_rd32(dev, i2c->wr) & 0xe0) | (state ? 0x10 : 0); + nv_wr32(dev, i2c->wr, val | 0x01); +} + +static int +nv4e_i2c_getscl(void *data) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + + return !!((nv_rd32(dev, i2c->rd) >> 16) & 4); +} + +static int +nv4e_i2c_getsda(void *data) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + + return !!((nv_rd32(dev, i2c->rd) >> 16) & 8); +} + +static int +nv50_i2c_getscl(void *data) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + + return !!(nv_rd32(dev, i2c->rd) & 1); +} + + +static int +nv50_i2c_getsda(void *data) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + + return !!(nv_rd32(dev, i2c->rd) & 2); +} + +static void +nv50_i2c_setscl(void *data, int state) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + + nv_wr32(dev, i2c->wr, 4 | (i2c->data ? 2 : 0) | (state ? 1 : 0)); +} + +static void +nv50_i2c_setsda(void *data, int state) +{ + struct nouveau_i2c_chan *i2c = data; + struct drm_device *dev = i2c->dev; + + nv_wr32(dev, i2c->wr, + (nv_rd32(dev, i2c->rd) & 1) | 4 | (state ? 2 : 0)); + i2c->data = state; +} + +static const uint32_t nv50_i2c_port[] = { + 0x00e138, 0x00e150, 0x00e168, 0x00e180, + 0x00e254, 0x00e274, 0x00e764, 0x00e780, + 0x00e79c, 0x00e7b8 +}; +#define NV50_I2C_PORTS ARRAY_SIZE(nv50_i2c_port) + +int +nouveau_i2c_init(struct drm_device *dev, struct dcb_i2c_entry *entry, int index) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_i2c_chan *i2c; + int ret; + + if (entry->chan) + return -EEXIST; + + if (dev_priv->card_type >= NV_50 && entry->read >= NV50_I2C_PORTS) { + NV_ERROR(dev, "unknown i2c port %d\n", entry->read); + return -EINVAL; + } + + i2c = kzalloc(sizeof(*i2c), GFP_KERNEL); + if (i2c == NULL) + return -ENOMEM; + + switch (entry->port_type) { + case 0: + i2c->bit.setsda = nv04_i2c_setsda; + i2c->bit.setscl = nv04_i2c_setscl; + i2c->bit.getsda = nv04_i2c_getsda; + i2c->bit.getscl = nv04_i2c_getscl; + i2c->rd = entry->read; + i2c->wr = entry->write; + break; + case 4: + i2c->bit.setsda = nv4e_i2c_setsda; + i2c->bit.setscl = nv4e_i2c_setscl; + i2c->bit.getsda = nv4e_i2c_getsda; + i2c->bit.getscl = nv4e_i2c_getscl; + i2c->rd = 0x600800 + entry->read; + i2c->wr = 0x600800 + entry->write; + break; + case 5: + i2c->bit.setsda = nv50_i2c_setsda; + i2c->bit.setscl = nv50_i2c_setscl; + i2c->bit.getsda = nv50_i2c_getsda; + i2c->bit.getscl = nv50_i2c_getscl; + i2c->rd = nv50_i2c_port[entry->read]; + i2c->wr = i2c->rd; + break; + case 6: + i2c->rd = entry->read; + i2c->wr = entry->write; + break; + default: + NV_ERROR(dev, "DCB I2C port type %d unknown\n", + entry->port_type); + kfree(i2c); + return -EINVAL; + } + + snprintf(i2c->adapter.name, sizeof(i2c->adapter.name), + "nouveau-%s-%d", pci_name(dev->pdev), index); + i2c->adapter.owner = THIS_MODULE; + i2c->adapter.dev.parent = &dev->pdev->dev; + i2c->dev = dev; + i2c_set_adapdata(&i2c->adapter, i2c); + + if (entry->port_type < 6) { + i2c->adapter.algo_data = &i2c->bit; + i2c->bit.udelay = 40; + i2c->bit.timeout = usecs_to_jiffies(5000); + i2c->bit.data = i2c; + ret = i2c_bit_add_bus(&i2c->adapter); + } else { + i2c->adapter.algo = &nouveau_dp_i2c_algo; + ret = i2c_add_adapter(&i2c->adapter); + } + + if (ret) { + NV_ERROR(dev, "Failed to register i2c %d\n", index); + kfree(i2c); + return ret; + } + + entry->chan = i2c; + return 0; +} + +void +nouveau_i2c_fini(struct drm_device *dev, struct dcb_i2c_entry *entry) +{ + if (!entry->chan) + return; + + i2c_del_adapter(&entry->chan->adapter); + kfree(entry->chan); + entry->chan = NULL; +} + +struct nouveau_i2c_chan * +nouveau_i2c_find(struct drm_device *dev, int index) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct dcb_i2c_entry *i2c = &dev_priv->vbios.dcb.i2c[index]; + + if (index >= DCB_MAX_NUM_I2C_ENTRIES) + return NULL; + + if (dev_priv->chipset >= NV_50 && (i2c->entry & 0x00000100)) { + uint32_t reg = 0xe500, val; + + if (i2c->port_type == 6) { + reg += i2c->read * 0x50; + val = 0x2002; + } else { + reg += ((i2c->entry & 0x1e00) >> 9) * 0x50; + val = 0xe001; + } + + nv_wr32(dev, reg, (nv_rd32(dev, reg) & ~0xf003) | val); + } + + if (!i2c->chan && nouveau_i2c_init(dev, i2c, index)) + return NULL; + return i2c->chan; +} + +bool +nouveau_probe_i2c_addr(struct nouveau_i2c_chan *i2c, int addr) +{ + uint8_t buf[] = { 0 }; + struct i2c_msg msgs[] = { + { + .addr = addr, + .flags = 0, + .len = 1, + .buf = buf, + }, + { + .addr = addr, + .flags = I2C_M_RD, + .len = 1, + .buf = buf, + } + }; + + return i2c_transfer(&i2c->adapter, msgs, 2) == 2; +} + +int +nouveau_i2c_identify(struct drm_device *dev, const char *what, + struct i2c_board_info *info, + bool (*match)(struct nouveau_i2c_chan *, + struct i2c_board_info *), + int index) +{ + struct nouveau_i2c_chan *i2c = nouveau_i2c_find(dev, index); + int i; + + NV_DEBUG(dev, "Probing %ss on I2C bus: %d\n", what, index); + + for (i = 0; info[i].addr; i++) { + if (nouveau_probe_i2c_addr(i2c, info[i].addr) && + (!match || match(i2c, &info[i]))) { + NV_INFO(dev, "Detected %s: %s\n", what, info[i].type); + return i; + } + } + + NV_DEBUG(dev, "No devices found.\n"); + + return -ENODEV; +} diff --git a/driver/pscnv/nouveau_i2c.h b/driver/pscnv/nouveau_i2c.h new file mode 100644 index 00000000..539b2c85 --- /dev/null +++ b/driver/pscnv/nouveau_i2c.h @@ -0,0 +1,58 @@ +/* + * Copyright 2009 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __NOUVEAU_I2C_H__ +#define __NOUVEAU_I2C_H__ + +#include +#ifdef PSCNV_KAPI_I2C_ID +#include +#else +#include +#endif +#include +#include "drm_dp_helper.h" + +struct dcb_i2c_entry; + +struct nouveau_i2c_chan { + struct i2c_adapter adapter; + struct drm_device *dev; + struct i2c_algo_bit_data bit; + unsigned rd; + unsigned wr; + unsigned data; +}; + +int nouveau_i2c_init(struct drm_device *, struct dcb_i2c_entry *, int index); +void nouveau_i2c_fini(struct drm_device *, struct dcb_i2c_entry *); +struct nouveau_i2c_chan *nouveau_i2c_find(struct drm_device *, int index); +bool nouveau_probe_i2c_addr(struct nouveau_i2c_chan *i2c, int addr); +int nouveau_i2c_identify(struct drm_device *dev, const char *what, + struct i2c_board_info *info, + bool (*match)(struct nouveau_i2c_chan *, + struct i2c_board_info *), + int index); + +extern const struct i2c_algorithm nouveau_dp_i2c_algo; + +#endif /* __NOUVEAU_I2C_H__ */ diff --git a/driver/pscnv/nouveau_ioc32.c b/driver/pscnv/nouveau_ioc32.c new file mode 100644 index 00000000..475ba810 --- /dev/null +++ b/driver/pscnv/nouveau_ioc32.c @@ -0,0 +1,70 @@ +/** + * \file mga_ioc32.c + * + * 32-bit ioctl compatibility routines for the MGA DRM. + * + * \author Dave Airlie with code from patches by Egbert Eich + * + * + * Copyright (C) Paul Mackerras 2005 + * Copyright (C) Egbert Eich 2003,2004 + * Copyright (C) Dave Airlie 2005 + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#include + +#include "drmP.h" +#include "drm.h" + +#include "nouveau_drv.h" + +/** + * Called whenever a 32-bit process running under a 64-bit kernel + * performs an ioctl on /dev/dri/card. + * + * \param filp file pointer. + * \param cmd command. + * \param arg user argument. + * \return zero on success or negative number on failure. + */ +long nouveau_compat_ioctl(struct file *filp, unsigned int cmd, + unsigned long arg) +{ + unsigned int nr = DRM_IOCTL_NR(cmd); + drm_ioctl_compat_t *fn = NULL; + int ret; + + if (nr < DRM_COMMAND_BASE) + return drm_compat_ioctl(filp, cmd, arg); + +#if 0 + if (nr < DRM_COMMAND_BASE + DRM_ARRAY_SIZE(mga_compat_ioctls)) + fn = nouveau_compat_ioctls[nr - DRM_COMMAND_BASE]; +#endif + if (fn != NULL) + ret = (*fn)(filp, cmd, arg); + else + ret = drm_ioctl(filp, cmd, arg); + + return ret; +} diff --git a/driver/pscnv/nouveau_irq.c b/driver/pscnv/nouveau_irq.c new file mode 100644 index 00000000..e5eade07 --- /dev/null +++ b/driver/pscnv/nouveau_irq.c @@ -0,0 +1,1330 @@ +/* + * Copyright (C) 2006 Ben Skeggs. + * + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +/* + * Authors: + * Ben Skeggs + */ + +#include "drmP.h" +#include "drm.h" +#include "pscnv_drm.h" +#include "nouveau_drv.h" +#include "nouveau_reg.h" +#include + +/* needed for hotplug irq */ +#include "nouveau_connector.h" +#include "nv50_display.h" +#include "pscnv_engine.h" +#include "pscnv_fifo.h" + +static DEFINE_RATELIMIT_STATE(nouveau_ratelimit_state, 3 * HZ, 20); + +static inline int nouveau_ratelimit(void) +{ + return __ratelimit(&nouveau_ratelimit_state); +} + +void +nouveau_irq_preinstall(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + /* Master disable */ + nv_wr32(dev, NV03_PMC_INTR_EN_0, 0); + + if (dev_priv->card_type >= NV_50) { + INIT_WORK(&dev_priv->irq_work, nv50_display_irq_handler_bh); + INIT_WORK(&dev_priv->hpd_work, nv50_display_irq_hotplug_bh); +// INIT_LIST_HEAD(&dev_priv->vbl_waiting); + } +} + +int +nouveau_irq_postinstall(struct drm_device *dev) +{ + /* Master enable */ + nv_wr32(dev, NV03_PMC_INTR_EN_0, NV_PMC_INTR_EN_0_MASTER_ENABLE); + return 0; +} + +void +nouveau_irq_uninstall(struct drm_device *dev) +{ + /* Master disable */ + nv_wr32(dev, NV03_PMC_INTR_EN_0, 0); +} + +#if 0 + +static int +nouveau_call_method(struct nouveau_channel *chan, int class, int mthd, int data) +{ + struct drm_nouveau_private *dev_priv = chan->dev->dev_private; + struct nouveau_pgraph_object_method *grm; + struct nouveau_pgraph_object_class *grc; + + grc = dev_priv->engine.graph.grclass; + while (grc->id) { + if (grc->id == class) + break; + grc++; + } + + if (grc->id != class || !grc->methods) + return -ENOENT; + + grm = grc->methods; + while (grm->id) { + if (grm->id == mthd) + return grm->exec(chan, class, mthd, data); + grm++; + } + + return -ENOENT; +} + +static bool +nouveau_fifo_swmthd(struct nouveau_channel *chan, uint32_t addr, uint32_t data) +{ + struct drm_device *dev = chan->dev; + const int subc = (addr >> 13) & 0x7; + const int mthd = addr & 0x1ffc; + + if (mthd == 0x0000) { + struct nouveau_gpuobj_ref *ref = NULL; + + if (nouveau_gpuobj_ref_find(chan, data, &ref)) + return false; + + if (ref->gpuobj->engine != NVOBJ_ENGINE_SW) + return false; + + chan->sw_subchannel[subc] = ref->gpuobj->class; + nv_wr32(dev, NV04_PFIFO_CACHE1_ENGINE, nv_rd32(dev, + NV04_PFIFO_CACHE1_ENGINE) & ~(0xf << subc * 4)); + return true; + } + + /* hw object */ + if (nv_rd32(dev, NV04_PFIFO_CACHE1_ENGINE) & (1 << (subc*4))) + return false; + + if (nouveau_call_method(chan, chan->sw_subchannel[subc], mthd, data)) + return false; + + return true; +} + +static void +nouveau_fifo_irq_handler(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_engine *engine = &dev_priv->engine; + uint32_t status, reassign; + int cnt = 0; + + reassign = nv_rd32(dev, NV03_PFIFO_CACHES) & 1; + while ((status = nv_rd32(dev, NV03_PFIFO_INTR_0)) && (cnt++ < 100)) { + struct nouveau_channel *chan = NULL; + uint32_t chid, get; + + nv_wr32(dev, NV03_PFIFO_CACHES, 0); + + chid = engine->fifo.channel_id(dev); + if (chid >= 0 && chid < engine->fifo.channels) + chan = dev_priv->fifos[chid]; + get = nv_rd32(dev, NV03_PFIFO_CACHE1_GET); + + if (status & NV_PFIFO_INTR_CACHE_ERROR) { + uint32_t mthd, data; + int ptr; + + /* NV_PFIFO_CACHE1_GET actually goes to 0xffc before + * wrapping on my G80 chips, but CACHE1 isn't big + * enough for this much data.. Tests show that it + * wraps around to the start at GET=0x800.. No clue + * as to why.. + */ + ptr = (get & 0x7ff) >> 2; + + if (dev_priv->card_type < NV_40) { + mthd = nv_rd32(dev, + NV04_PFIFO_CACHE1_METHOD(ptr)); + data = nv_rd32(dev, + NV04_PFIFO_CACHE1_DATA(ptr)); + } else { + mthd = nv_rd32(dev, + NV40_PFIFO_CACHE1_METHOD(ptr)); + data = nv_rd32(dev, + NV40_PFIFO_CACHE1_DATA(ptr)); + } + + if (!chan || !nouveau_fifo_swmthd(chan, mthd, data)) { + NV_INFO(dev, "PFIFO_CACHE_ERROR - Ch %d/%d " + "Mthd 0x%04x Data 0x%08x\n", + chid, (mthd >> 13) & 7, mthd & 0x1ffc, + data); + } + + nv_wr32(dev, NV04_PFIFO_CACHE1_DMA_PUSH, 0); + nv_wr32(dev, NV03_PFIFO_INTR_0, + NV_PFIFO_INTR_CACHE_ERROR); + + nv_wr32(dev, NV03_PFIFO_CACHE1_PUSH0, + nv_rd32(dev, NV03_PFIFO_CACHE1_PUSH0) & ~1); + nv_wr32(dev, NV03_PFIFO_CACHE1_GET, get + 4); + nv_wr32(dev, NV03_PFIFO_CACHE1_PUSH0, + nv_rd32(dev, NV03_PFIFO_CACHE1_PUSH0) | 1); + nv_wr32(dev, NV04_PFIFO_CACHE1_HASH, 0); + + nv_wr32(dev, NV04_PFIFO_CACHE1_DMA_PUSH, + nv_rd32(dev, NV04_PFIFO_CACHE1_DMA_PUSH) | 1); + nv_wr32(dev, NV04_PFIFO_CACHE1_PULL0, 1); + + status &= ~NV_PFIFO_INTR_CACHE_ERROR; + } + + if (status & NV_PFIFO_INTR_DMA_PUSHER) { + NV_INFO(dev, "PFIFO_DMA_PUSHER - Ch %d\n", chid); + + status &= ~NV_PFIFO_INTR_DMA_PUSHER; + nv_wr32(dev, NV03_PFIFO_INTR_0, + NV_PFIFO_INTR_DMA_PUSHER); + + nv_wr32(dev, NV04_PFIFO_CACHE1_DMA_STATE, 0x00000000); + if (nv_rd32(dev, NV04_PFIFO_CACHE1_DMA_PUT) != get) + nv_wr32(dev, NV04_PFIFO_CACHE1_DMA_GET, + get + 4); + } + + if (status & NV_PFIFO_INTR_SEMAPHORE) { + uint32_t sem; + + status &= ~NV_PFIFO_INTR_SEMAPHORE; + nv_wr32(dev, NV03_PFIFO_INTR_0, + NV_PFIFO_INTR_SEMAPHORE); + + sem = nv_rd32(dev, NV10_PFIFO_CACHE1_SEMAPHORE); + nv_wr32(dev, NV10_PFIFO_CACHE1_SEMAPHORE, sem | 0x1); + + nv_wr32(dev, NV03_PFIFO_CACHE1_GET, get + 4); + nv_wr32(dev, NV04_PFIFO_CACHE1_PULL0, 1); + } + + if (status) { + NV_INFO(dev, "PFIFO_INTR 0x%08x - Ch %d\n", + status, chid); + nv_wr32(dev, NV03_PFIFO_INTR_0, status); + status = 0; + } + + nv_wr32(dev, NV03_PFIFO_CACHES, reassign); + } + + if (status) { + NV_INFO(dev, "PFIFO still angry after %d spins, halt\n", cnt); + nv_wr32(dev, 0x2140, 0); + nv_wr32(dev, 0x140, 0); + } + + nv_wr32(dev, NV03_PMC_INTR_0, NV_PMC_INTR_0_PFIFO_PENDING); +} + +struct nouveau_bitfield_names { + uint32_t mask; + const char *name; +}; + +static struct nouveau_bitfield_names nstatus_names[] = +{ + { NV04_PGRAPH_NSTATUS_STATE_IN_USE, "STATE_IN_USE" }, + { NV04_PGRAPH_NSTATUS_INVALID_STATE, "INVALID_STATE" }, + { NV04_PGRAPH_NSTATUS_BAD_ARGUMENT, "BAD_ARGUMENT" }, + { NV04_PGRAPH_NSTATUS_PROTECTION_FAULT, "PROTECTION_FAULT" } +}; + +static struct nouveau_bitfield_names nstatus_names_nv10[] = +{ + { NV10_PGRAPH_NSTATUS_STATE_IN_USE, "STATE_IN_USE" }, + { NV10_PGRAPH_NSTATUS_INVALID_STATE, "INVALID_STATE" }, + { NV10_PGRAPH_NSTATUS_BAD_ARGUMENT, "BAD_ARGUMENT" }, + { NV10_PGRAPH_NSTATUS_PROTECTION_FAULT, "PROTECTION_FAULT" } +}; + +static struct nouveau_bitfield_names nsource_names[] = +{ + { NV03_PGRAPH_NSOURCE_NOTIFICATION, "NOTIFICATION" }, + { NV03_PGRAPH_NSOURCE_DATA_ERROR, "DATA_ERROR" }, + { NV03_PGRAPH_NSOURCE_PROTECTION_ERROR, "PROTECTION_ERROR" }, + { NV03_PGRAPH_NSOURCE_RANGE_EXCEPTION, "RANGE_EXCEPTION" }, + { NV03_PGRAPH_NSOURCE_LIMIT_COLOR, "LIMIT_COLOR" }, + { NV03_PGRAPH_NSOURCE_LIMIT_ZETA, "LIMIT_ZETA" }, + { NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD, "ILLEGAL_MTHD" }, + { NV03_PGRAPH_NSOURCE_DMA_R_PROTECTION, "DMA_R_PROTECTION" }, + { NV03_PGRAPH_NSOURCE_DMA_W_PROTECTION, "DMA_W_PROTECTION" }, + { NV03_PGRAPH_NSOURCE_FORMAT_EXCEPTION, "FORMAT_EXCEPTION" }, + { NV03_PGRAPH_NSOURCE_PATCH_EXCEPTION, "PATCH_EXCEPTION" }, + { NV03_PGRAPH_NSOURCE_STATE_INVALID, "STATE_INVALID" }, + { NV03_PGRAPH_NSOURCE_DOUBLE_NOTIFY, "DOUBLE_NOTIFY" }, + { NV03_PGRAPH_NSOURCE_NOTIFY_IN_USE, "NOTIFY_IN_USE" }, + { NV03_PGRAPH_NSOURCE_METHOD_CNT, "METHOD_CNT" }, + { NV03_PGRAPH_NSOURCE_BFR_NOTIFICATION, "BFR_NOTIFICATION" }, + { NV03_PGRAPH_NSOURCE_DMA_VTX_PROTECTION, "DMA_VTX_PROTECTION" }, + { NV03_PGRAPH_NSOURCE_DMA_WIDTH_A, "DMA_WIDTH_A" }, + { NV03_PGRAPH_NSOURCE_DMA_WIDTH_B, "DMA_WIDTH_B" }, +}; + +static void +nouveau_print_bitfield_names_(uint32_t value, + const struct nouveau_bitfield_names *namelist, + const int namelist_len) +{ + /* + * Caller must have already printed the KERN_* log level for us. + * Also the caller is responsible for adding the newline. + */ + int i; + for (i = 0; i < namelist_len; ++i) { + uint32_t mask = namelist[i].mask; + if (value & mask) { + printk(" %s", namelist[i].name); + value &= ~mask; + } + } + if (value) + printk(" (unknown bits 0x%08x)", value); +} +#define nouveau_print_bitfield_names(val, namelist) \ + nouveau_print_bitfield_names_((val), (namelist), ARRAY_SIZE(namelist)) + +struct nouveau_enum_names { + uint32_t value; + const char *name; +}; + +static void +nouveau_print_enum_names_(uint32_t value, + const struct nouveau_enum_names *namelist, + const int namelist_len) +{ + /* + * Caller must have already printed the KERN_* log level for us. + * Also the caller is responsible for adding the newline. + */ + int i; + for (i = 0; i < namelist_len; ++i) { + if (value == namelist[i].value) { + printk("%s", namelist[i].name); + return; + } + } + printk("unknown value 0x%08x", value); +} +#define nouveau_print_enum_names(val, namelist) \ + nouveau_print_enum_names_((val), (namelist), ARRAY_SIZE(namelist)) + +static int +nouveau_graph_chid_from_grctx(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t inst; + int i; + + if (dev_priv->card_type < NV_40) + return dev_priv->engine.fifo.channels; + else + if (dev_priv->card_type < NV_50) { + inst = (nv_rd32(dev, 0x40032c) & 0xfffff) << 4; + + for (i = 0; i < dev_priv->engine.fifo.channels; i++) { + struct nouveau_channel *chan = dev_priv->fifos[i]; + + if (!chan || !chan->ramin_grctx) + continue; + + if (inst == chan->ramin_grctx->instance) + break; + } + } else { + inst = (nv_rd32(dev, 0x40032c) & 0xfffff) << 12; + + for (i = 0; i < dev_priv->engine.fifo.channels; i++) { + struct nouveau_channel *chan = dev_priv->fifos[i]; + + if (!chan || !chan->ramin) + continue; + + if (inst == chan->ramin->instance) + break; + } + } + + + return i; +} + +static int +nouveau_graph_trapped_channel(struct drm_device *dev, int *channel_ret) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_engine *engine = &dev_priv->engine; + int channel; + + if (dev_priv->card_type < NV_10) + channel = (nv_rd32(dev, NV04_PGRAPH_TRAPPED_ADDR) >> 24) & 0xf; + else + if (dev_priv->card_type < NV_40) + channel = (nv_rd32(dev, NV04_PGRAPH_TRAPPED_ADDR) >> 20) & 0x1f; + else + channel = nouveau_graph_chid_from_grctx(dev); + + if (channel >= engine->fifo.channels || !dev_priv->fifos[channel]) { + NV_ERROR(dev, "AIII, invalid/inactive channel id %d\n", channel); + return -EINVAL; + } + + *channel_ret = channel; + return 0; +} + +struct nouveau_pgraph_trap { + int channel; + int class; + int subc, mthd, size; + uint32_t data, data2; + uint32_t nsource, nstatus; +}; + +static void +nouveau_graph_trap_info(struct drm_device *dev, + struct nouveau_pgraph_trap *trap) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t address; + + trap->nsource = trap->nstatus = 0; + if (dev_priv->card_type < NV_50) { + trap->nsource = nv_rd32(dev, NV03_PGRAPH_NSOURCE); + trap->nstatus = nv_rd32(dev, NV03_PGRAPH_NSTATUS); + } + + if (nouveau_graph_trapped_channel(dev, &trap->channel)) + trap->channel = -1; + address = nv_rd32(dev, NV04_PGRAPH_TRAPPED_ADDR); + + trap->mthd = address & 0x1FFC; + trap->data = nv_rd32(dev, NV04_PGRAPH_TRAPPED_DATA); + if (dev_priv->card_type < NV_10) { + trap->subc = (address >> 13) & 0x7; + } else { + trap->subc = (address >> 16) & 0x7; + trap->data2 = nv_rd32(dev, NV10_PGRAPH_TRAPPED_DATA_HIGH); + } + + if (dev_priv->card_type < NV_10) + trap->class = nv_rd32(dev, 0x400180 + trap->subc*4) & 0xFF; + else if (dev_priv->card_type < NV_40) + trap->class = nv_rd32(dev, 0x400160 + trap->subc*4) & 0xFFF; + else if (dev_priv->card_type < NV_50) + trap->class = nv_rd32(dev, 0x400160 + trap->subc*4) & 0xFFFF; + else + trap->class = nv_rd32(dev, 0x400814); +} + +static void +nouveau_graph_dump_trap_info(struct drm_device *dev, const char *id, + struct nouveau_pgraph_trap *trap) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t nsource = trap->nsource, nstatus = trap->nstatus; + + if (dev_priv->card_type < NV_50) { + NV_INFO(dev, "%s - nSource:", id); + nouveau_print_bitfield_names(nsource, nsource_names); + printk(", nStatus:"); + if (dev_priv->card_type < NV_10) + nouveau_print_bitfield_names(nstatus, nstatus_names); + else + nouveau_print_bitfield_names(nstatus, nstatus_names_nv10); + printk("\n"); + } + + NV_INFO(dev, "%s - Ch %d/%d Class 0x%04x Mthd 0x%04x " + "Data 0x%08x:0x%08x\n", + id, trap->channel, trap->subc, + trap->class, trap->mthd, + trap->data2, trap->data); +} + +static int +nouveau_pgraph_intr_swmthd(struct drm_device *dev, + struct nouveau_pgraph_trap *trap) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + if (trap->channel < 0 || + trap->channel >= dev_priv->engine.fifo.channels || + !dev_priv->fifos[trap->channel]) + return -ENODEV; + + return nouveau_call_method(dev_priv->fifos[trap->channel], + trap->class, trap->mthd, trap->data); +} + +static inline void +nouveau_pgraph_intr_notify(struct drm_device *dev, uint32_t nsource) +{ + struct nouveau_pgraph_trap trap; + int unhandled = 0; + + nouveau_graph_trap_info(dev, &trap); + + if (nsource & NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD) { + if (nouveau_pgraph_intr_swmthd(dev, &trap)) + unhandled = 1; + } else { + unhandled = 1; + } + + if (unhandled) + nouveau_graph_dump_trap_info(dev, "PGRAPH_NOTIFY", &trap); +} + + +static inline void +nouveau_pgraph_intr_error(struct drm_device *dev, uint32_t nsource) +{ + struct nouveau_pgraph_trap trap; + int unhandled = 0; + + nouveau_graph_trap_info(dev, &trap); + trap.nsource = nsource; + + if (nsource & NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD) { + if (nouveau_pgraph_intr_swmthd(dev, &trap)) + unhandled = 1; + } else if (nsource & NV03_PGRAPH_NSOURCE_DMA_VTX_PROTECTION) { + uint32_t v = nv_rd32(dev, 0x402000); + nv_wr32(dev, 0x402000, v); + + /* dump the error anyway for now: it's useful for + Gallium development */ + unhandled = 1; + } else { + unhandled = 1; + } + + if (unhandled && nouveau_ratelimit()) + nouveau_graph_dump_trap_info(dev, "PGRAPH_ERROR", &trap); +} + +static inline void +nouveau_pgraph_intr_context_switch(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_engine *engine = &dev_priv->engine; + uint32_t chid; + + chid = engine->fifo.channel_id(dev); + NV_DEBUG(dev, "PGRAPH context switch interrupt channel %x\n", chid); + + switch (dev_priv->card_type) { + case NV_04: + nv04_graph_context_switch(dev); + break; + case NV_10: + nv10_graph_context_switch(dev); + break; + default: + NV_ERROR(dev, "Context switch not implemented\n"); + break; + } +} + +static void +nouveau_pgraph_irq_handler(struct drm_device *dev) +{ + uint32_t status; + + while ((status = nv_rd32(dev, NV03_PGRAPH_INTR))) { + uint32_t nsource = nv_rd32(dev, NV03_PGRAPH_NSOURCE); + + if (status & NV_PGRAPH_INTR_NOTIFY) { + nouveau_pgraph_intr_notify(dev, nsource); + + status &= ~NV_PGRAPH_INTR_NOTIFY; + nv_wr32(dev, NV03_PGRAPH_INTR, NV_PGRAPH_INTR_NOTIFY); + } + + if (status & NV_PGRAPH_INTR_ERROR) { + nouveau_pgraph_intr_error(dev, nsource); + + status &= ~NV_PGRAPH_INTR_ERROR; + nv_wr32(dev, NV03_PGRAPH_INTR, NV_PGRAPH_INTR_ERROR); + } + + if (status & NV_PGRAPH_INTR_CONTEXT_SWITCH) { + nouveau_pgraph_intr_context_switch(dev); + + status &= ~NV_PGRAPH_INTR_CONTEXT_SWITCH; + nv_wr32(dev, NV03_PGRAPH_INTR, + NV_PGRAPH_INTR_CONTEXT_SWITCH); + } + + if (status) { + NV_INFO(dev, "Unhandled PGRAPH_INTR - 0x%08x\n", status); + nv_wr32(dev, NV03_PGRAPH_INTR, status); + } + + if ((nv_rd32(dev, NV04_PGRAPH_FIFO) & (1 << 0)) == 0) + nv_wr32(dev, NV04_PGRAPH_FIFO, 1); + } + + nv_wr32(dev, NV03_PMC_INTR_0, NV_PMC_INTR_0_PGRAPH_PENDING); +} + +static void +nv50_pfb_vm_trap(struct drm_device *dev, int display, const char *name) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t trap[6]; + int i, ch; + uint32_t idx = nv_rd32(dev, 0x100c90); + if (idx & 0x80000000) { + idx &= 0xffffff; + if (display) { + for (i = 0; i < 6; i++) { + nv_wr32(dev, 0x100c90, idx | i << 24); + trap[i] = nv_rd32(dev, 0x100c94); + } + for (ch = 0; ch < dev_priv->engine.fifo.channels; ch++) { + struct nouveau_channel *chan = dev_priv->fifos[ch]; + + if (!chan || !chan->ramin) + continue; + + if (trap[1] == chan->ramin->instance >> 12) + break; + } + NV_INFO(dev, "%s - VM: Trapped %s at %02x%04x%04x status %08x %08x channel %d\n", + name, (trap[5]&0x100?"read":"write"), + trap[5]&0xff, trap[4]&0xffff, + trap[3]&0xffff, trap[0], trap[2], ch); + } + nv_wr32(dev, 0x100c90, idx | 0x80000000); + } else if (display) { + NV_INFO(dev, "%s - no VM fault?\n", name); + } +} + +static struct nouveau_enum_names nv50_mp_exec_error_names[] = +{ + { 3, "STACK_UNDERFLOW" }, + { 4, "QUADON_ACTIVE" }, + { 8, "TIMEOUT" }, + { 0x10, "INVALID_OPCODE" }, + { 0x40, "BREAKPOINT" }, +}; + +static void +nv50_pgraph_mp_trap(struct drm_device *dev, int tpid, int display) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t units = nv_rd32(dev, 0x1540); + uint32_t addr, mp10, status, pc, oplow, ophigh; + int i; + int mps = 0; + for (i = 0; i < 4; i++) { + if (!(units & 1 << (i+24))) + continue; + if (dev_priv->chipset < 0xa0) + addr = 0x408200 + (tpid << 12) + (i << 7); + else + addr = 0x408100 + (tpid << 11) + (i << 7); + mp10 = nv_rd32(dev, addr + 0x10); + status = nv_rd32(dev, addr + 0x14); + if (!status) + continue; + if (display) { + nv_rd32(dev, addr + 0x20); + pc = nv_rd32(dev, addr + 0x24); + oplow = nv_rd32(dev, addr + 0x70); + ophigh= nv_rd32(dev, addr + 0x74); + NV_INFO(dev, "PGRAPH_TRAP_MP_EXEC - " + "TP %d MP %d: ", tpid, i); + nouveau_print_enum_names(status, + nv50_mp_exec_error_names); + printk(" at %06x warp %d, opcode %08x %08x\n", + pc&0xffffff, pc >> 24, + oplow, ophigh); + } + nv_wr32(dev, addr + 0x10, mp10); + nv_wr32(dev, addr + 0x14, 0); + mps++; + } + if (!mps && display) + NV_INFO(dev, "PGRAPH_TRAP_MP_EXEC - TP %d: " + "No MPs claiming errors?\n", tpid); +} + +static void +nv50_pgraph_tp_trap(struct drm_device *dev, int type, uint32_t ustatus_old, + uint32_t ustatus_new, int display, const char *name) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int tps = 0; + uint32_t units = nv_rd32(dev, 0x1540); + int i, r; + uint32_t ustatus_addr, ustatus; + for (i = 0; i < 16; i++) { + if (!(units & (1 << i))) + continue; + if (dev_priv->chipset < 0xa0) + ustatus_addr = ustatus_old + (i << 12); + else + ustatus_addr = ustatus_new + (i << 11); + ustatus = nv_rd32(dev, ustatus_addr) & 0x7fffffff; + if (!ustatus) + continue; + tps++; + switch (type) { + case 6: /* texture error... unknown for now */ + nv50_pfb_vm_trap(dev, display, name); + if (display) { + NV_ERROR(dev, "magic set %d:\n", i); + for (r = ustatus_addr + 4; r <= ustatus_addr + 0x10; r += 4) + NV_ERROR(dev, "\t0x%08x: 0x%08x\n", r, + nv_rd32(dev, r)); + } + break; + case 7: /* MP error */ + if (ustatus & 0x00010000) { + nv50_pgraph_mp_trap(dev, i, display); + ustatus &= ~0x00010000; + } + break; + case 8: /* TPDMA error */ + { + uint32_t e0c = nv_rd32(dev, ustatus_addr + 4); + uint32_t e10 = nv_rd32(dev, ustatus_addr + 8); + uint32_t e14 = nv_rd32(dev, ustatus_addr + 0xc); + uint32_t e18 = nv_rd32(dev, ustatus_addr + 0x10); + uint32_t e1c = nv_rd32(dev, ustatus_addr + 0x14); + uint32_t e20 = nv_rd32(dev, ustatus_addr + 0x18); + uint32_t e24 = nv_rd32(dev, ustatus_addr + 0x1c); + nv50_pfb_vm_trap(dev, display, name); + /* 2d engine destination */ + if (ustatus & 0x00000010) { + if (display) { + NV_INFO(dev, "PGRAPH_TRAP_TPDMA_2D - TP %d - Unknown fault at address %02x%08x\n", + i, e14, e10); + NV_INFO(dev, "PGRAPH_TRAP_TPDMA_2D - TP %d - e0c: %08x, e18: %08x, e1c: %08x, e20: %08x, e24: %08x\n", + i, e0c, e18, e1c, e20, e24); + } + ustatus &= ~0x00000010; + } + /* Render target */ + if (ustatus & 0x00000040) { + if (display) { + NV_INFO(dev, "PGRAPH_TRAP_TPDMA_RT - TP %d - Unknown fault at address %02x%08x\n", + i, e14, e10); + NV_INFO(dev, "PGRAPH_TRAP_TPDMA_RT - TP %d - e0c: %08x, e18: %08x, e1c: %08x, e20: %08x, e24: %08x\n", + i, e0c, e18, e1c, e20, e24); + } + ustatus &= ~0x00000040; + } + /* CUDA memory: l[], g[] or stack. */ + if (ustatus & 0x00000080) { + if (display) { + if (e18 & 0x80000000) { + /* g[] read fault? */ + NV_INFO(dev, "PGRAPH_TRAP_TPDMA - TP %d - Global read fault at address %02x%08x\n", + i, e14, e10 | ((e18 >> 24) & 0x1f)); + e18 &= ~0x1f000000; + } else if (e18 & 0xc) { + /* g[] write fault? */ + NV_INFO(dev, "PGRAPH_TRAP_TPDMA - TP %d - Global write fault at address %02x%08x\n", + i, e14, e10 | ((e18 >> 7) & 0x1f)); + e18 &= ~0x00000f80; + } else { + NV_INFO(dev, "PGRAPH_TRAP_TPDMA - TP %d - Unknown CUDA fault at address %02x%08x\n", + i, e14, e10); + } + NV_INFO(dev, "PGRAPH_TRAP_TPDMA - TP %d - e0c: %08x, e18: %08x, e1c: %08x, e20: %08x, e24: %08x\n", + i, e0c, e18, e1c, e20, e24); + } + ustatus &= ~0x00000080; + } + } + break; + } + if (ustatus) { + if (display) + NV_INFO(dev, "%s - TP%d: Unhandled ustatus 0x%08x\n", name, i, ustatus); + } + nv_wr32(dev, ustatus_addr, 0xc0000000); + } + + if (!tps && display) + NV_INFO(dev, "%s - No TPs claiming errors?\n", name); +} + +static void +nv50_pgraph_trap_handler(struct drm_device *dev) +{ + struct nouveau_pgraph_trap trap; + uint32_t status = nv_rd32(dev, 0x400108); + uint32_t ustatus; + int display = nouveau_ratelimit(); + + + if (!status && display) { + nouveau_graph_trap_info(dev, &trap); + nouveau_graph_dump_trap_info(dev, "PGRAPH_TRAP", &trap); + NV_INFO(dev, "PGRAPH_TRAP - no units reporting traps?\n"); + } + + /* DISPATCH: Relays commands to other units and handles NOTIFY, + * COND, QUERY. If you get a trap from it, the command is still stuck + * in DISPATCH and you need to do something about it. */ + if (status & 0x001) { + ustatus = nv_rd32(dev, 0x400804) & 0x7fffffff; + if (!ustatus && display) { + NV_INFO(dev, "PGRAPH_TRAP_DISPATCH - no ustatus?\n"); + } + + /* Known to be triggered by screwed up NOTIFY and COND... */ + if (ustatus & 0x00000001) { + nv50_pfb_vm_trap(dev, display, "PGRAPH_TRAP_DISPATCH_FAULT"); + nv_wr32(dev, 0x400500, 0); + if (nv_rd32(dev, 0x400808) & 0x80000000) { + if (display) { + if (nouveau_graph_trapped_channel(dev, &trap.channel)) + trap.channel = -1; + trap.class = nv_rd32(dev, 0x400814); + trap.mthd = nv_rd32(dev, 0x400808) & 0x1ffc; + trap.subc = (nv_rd32(dev, 0x400808) >> 16) & 0x7; + trap.data = nv_rd32(dev, 0x40080c); + trap.data2 = nv_rd32(dev, 0x400810); + nouveau_graph_dump_trap_info(dev, + "PGRAPH_TRAP_DISPATCH_FAULT", &trap); + NV_INFO(dev, "PGRAPH_TRAP_DISPATCH_FAULT - 400808: %08x\n", nv_rd32(dev, 0x400808)); + NV_INFO(dev, "PGRAPH_TRAP_DISPATCH_FAULT - 400848: %08x\n", nv_rd32(dev, 0x400848)); + } + nv_wr32(dev, 0x400808, 0); + } else if (display) { + NV_INFO(dev, "PGRAPH_TRAP_DISPATCH_FAULT - No stuck command?\n"); + } + nv_wr32(dev, 0x4008e8, nv_rd32(dev, 0x4008e8) & 3); + nv_wr32(dev, 0x400848, 0); + ustatus &= ~0x00000001; + } + if (ustatus & 0x00000002) { + nv50_pfb_vm_trap(dev, display, "PGRAPH_TRAP_DISPATCH_QUERY"); + nv_wr32(dev, 0x400500, 0); + if (nv_rd32(dev, 0x40084c) & 0x80000000) { + if (display) { + if (nouveau_graph_trapped_channel(dev, &trap.channel)) + trap.channel = -1; + trap.class = nv_rd32(dev, 0x400814); + trap.mthd = nv_rd32(dev, 0x40084c) & 0x1ffc; + trap.subc = (nv_rd32(dev, 0x40084c) >> 16) & 0x7; + trap.data = nv_rd32(dev, 0x40085c); + trap.data2 = 0; + nouveau_graph_dump_trap_info(dev, + "PGRAPH_TRAP_DISPATCH_QUERY", &trap); + NV_INFO(dev, "PGRAPH_TRAP_DISPATCH_QUERY - 40084c: %08x\n", nv_rd32(dev, 0x40084c)); + } + nv_wr32(dev, 0x40084c, 0); + } else if (display) { + NV_INFO(dev, "PGRAPH_TRAP_DISPATCH_QUERY - No stuck command?\n"); + } + ustatus &= ~0x00000002; + } + if (ustatus && display) + NV_INFO(dev, "PGRAPH_TRAP_DISPATCH - Unhandled ustatus 0x%08x\n", ustatus); + nv_wr32(dev, 0x400804, 0xc0000000); + nv_wr32(dev, 0x400108, 0x001); + status &= ~0x001; + } + + /* TRAPs other than dispatch use the "normal" trap regs. */ + if (status && display) { + nouveau_graph_trap_info(dev, &trap); + nouveau_graph_dump_trap_info(dev, + "PGRAPH_TRAP", &trap); + } + + /* M2MF: Memory to memory copy engine. */ + if (status & 0x002) { + ustatus = nv_rd32(dev, 0x406800) & 0x7fffffff; + if (!ustatus && display) { + NV_INFO(dev, "PGRAPH_TRAP_M2MF - no ustatus?\n"); + } + if (ustatus & 0x00000001) { + nv50_pfb_vm_trap(dev, display, "PGRAPH_TRAP_M2MF_NOTIFY"); + ustatus &= ~0x00000001; + } + if (ustatus & 0x00000002) { + nv50_pfb_vm_trap(dev, display, "PGRAPH_TRAP_M2MF_IN"); + ustatus &= ~0x00000002; + } + if (ustatus & 0x00000004) { + nv50_pfb_vm_trap(dev, display, "PGRAPH_TRAP_M2MF_OUT"); + ustatus &= ~0x00000004; + } + NV_INFO (dev, "PGRAPH_TRAP_M2MF - %08x %08x %08x %08x\n", + nv_rd32(dev, 0x406804), + nv_rd32(dev, 0x406808), + nv_rd32(dev, 0x40680c), + nv_rd32(dev, 0x406810)); + if (ustatus && display) + NV_INFO(dev, "PGRAPH_TRAP_M2MF - Unhandled ustatus 0x%08x\n", ustatus); + /* No sane way found yet -- just reset the bugger. */ + nv_wr32(dev, 0x400040, 2); + nv_wr32(dev, 0x400040, 0); + nv_wr32(dev, 0x406800, 0xc0000000); + nv_wr32(dev, 0x400108, 0x002); + status &= ~0x002; + } + + /* VFETCH: Fetches data from vertex buffers. */ + if (status & 0x004) { + ustatus = nv_rd32(dev, 0x400c04) & 0x7fffffff; + if (!ustatus && display) { + NV_INFO(dev, "PGRAPH_TRAP_VFETCH - no ustatus?\n"); + } + if (ustatus & 0x00000001) { + nv50_pfb_vm_trap(dev, display, "PGRAPH_TRAP_VFETCH_FAULT"); + NV_INFO (dev, "PGRAPH_TRAP_VFETCH_FAULT - %08x %08x %08x %08x\n", + nv_rd32(dev, 0x400c00), + nv_rd32(dev, 0x400c08), + nv_rd32(dev, 0x400c0c), + nv_rd32(dev, 0x400c10)); + ustatus &= ~0x00000001; + } + if (ustatus && display) + NV_INFO(dev, "PGRAPH_TRAP_VFETCH - Unhandled ustatus 0x%08x\n", ustatus); + nv_wr32(dev, 0x400c04, 0xc0000000); + nv_wr32(dev, 0x400108, 0x004); + status &= ~0x004; + } + + /* STRMOUT: DirectX streamout / OpenGL transform feedback. */ + if (status & 0x008) { + ustatus = nv_rd32(dev, 0x401800) & 0x7fffffff; + if (!ustatus && display) { + NV_INFO(dev, "PGRAPH_TRAP_STRMOUT - no ustatus?\n"); + } + if (ustatus & 0x00000001) { + nv50_pfb_vm_trap(dev, display, "PGRAPH_TRAP_STRMOUT_FAULT"); + NV_INFO (dev, "PGRAPH_TRAP_STRMOUT_FAULT - %08x %08x %08x %08x\n", + nv_rd32(dev, 0x401804), + nv_rd32(dev, 0x401808), + nv_rd32(dev, 0x40180c), + nv_rd32(dev, 0x401810)); + ustatus &= ~0x00000001; + } + if (ustatus && display) + NV_INFO(dev, "PGRAPH_TRAP_STRMOUT - Unhandled ustatus 0x%08x\n", ustatus); + /* No sane way found yet -- just reset the bugger. */ + nv_wr32(dev, 0x400040, 0x80); + nv_wr32(dev, 0x400040, 0); + nv_wr32(dev, 0x401800, 0xc0000000); + nv_wr32(dev, 0x400108, 0x008); + status &= ~0x008; + } + + /* CCACHE: Handles code and c[] caches and fills them. */ + if (status & 0x010) { + ustatus = nv_rd32(dev, 0x405018) & 0x7fffffff; + if (!ustatus && display) { + NV_INFO(dev, "PGRAPH_TRAP_CCACHE - no ustatus?\n"); + } + if (ustatus & 0x00000001) { + nv50_pfb_vm_trap(dev, display, "PGRAPH_TRAP_CCACHE_FAULT"); + NV_INFO (dev, "PGRAPH_TRAP_CCACHE_FAULT - %08x %08x %08x %08x %08x %08x %08x\n", + nv_rd32(dev, 0x405800), + nv_rd32(dev, 0x405804), + nv_rd32(dev, 0x405808), + nv_rd32(dev, 0x40580c), + nv_rd32(dev, 0x405810), + nv_rd32(dev, 0x405814), + nv_rd32(dev, 0x40581c)); + ustatus &= ~0x00000001; + } + if (ustatus && display) + NV_INFO(dev, "PGRAPH_TRAP_CCACHE - Unhandled ustatus 0x%08x\n", ustatus); + nv_wr32(dev, 0x405018, 0xc0000000); + nv_wr32(dev, 0x400108, 0x010); + status &= ~0x010; + } + + /* Unknown, not seen yet... 0x402000 is the only trap status reg + * remaining, so try to handle it anyway. Perhaps related to that + * unknown DMA slot on tesla? */ + if (status & 0x20) { + nv50_pfb_vm_trap(dev, display, "PGRAPH_TRAP_UNKC04"); + ustatus = nv_rd32(dev, 0x402000) & 0x7fffffff; + if (display) + NV_INFO(dev, "PGRAPH_TRAP_UNKC04 - Unhandled ustatus 0x%08x\n", ustatus); + nv_wr32(dev, 0x402000, 0xc0000000); + /* no status modifiction on purpose */ + } + + /* TEXTURE: CUDA texturing units */ + if (status & 0x040) { + nv50_pgraph_tp_trap (dev, 6, 0x408900, 0x408600, display, + "PGRAPH_TRAP_TEXTURE"); + nv_wr32(dev, 0x400108, 0x040); + status &= ~0x040; + } + + /* MP: CUDA execution engines. */ + if (status & 0x080) { + nv50_pgraph_tp_trap (dev, 7, 0x408314, 0x40831c, display, + "PGRAPH_TRAP_MP"); + nv_wr32(dev, 0x400108, 0x080); + status &= ~0x080; + } + + /* TPDMA: Handles TP-initiated uncached memory accesses: + * l[], g[], stack, 2d surfaces, render targets. */ + if (status & 0x100) { + nv50_pgraph_tp_trap (dev, 8, 0x408e08, 0x408708, display, + "PGRAPH_TRAP_TPDMA"); + nv_wr32(dev, 0x400108, 0x100); + status &= ~0x100; + } + + if (status) { + if (display) + NV_INFO(dev, "PGRAPH_TRAP - Unknown trap 0x%08x\n", + status); + nv_wr32(dev, 0x400108, status); + } +} + +/* There must be a *lot* of these. Will take some time to gather them up. */ +static struct nouveau_enum_names nv50_data_error_names[] = +{ + { 4, "INVALID_VALUE" }, + { 5, "INVALID_ENUM" }, + { 8, "INVALID_OBJECT" }, + { 0xc, "INVALID_BITFIELD" }, + { 0x28, "MP_NO_REG_SPACE" }, + { 0x2b, "MP_BLOCK_SIZE_MISMATCH" }, +}; + +static void +nv50_pgraph_irq_handler(struct drm_device *dev) +{ + struct nouveau_pgraph_trap trap; + int unhandled = 0; + uint32_t status; + + while ((status = nv_rd32(dev, NV03_PGRAPH_INTR))) { + /* NOTIFY: You've set a NOTIFY an a command and it's done. */ + if (status & 0x00000001) { + nouveau_graph_trap_info(dev, &trap); + if (nouveau_ratelimit()) + nouveau_graph_dump_trap_info(dev, + "PGRAPH_NOTIFY", &trap); + status &= ~0x00000001; + nv_wr32(dev, NV03_PGRAPH_INTR, 0x00000001); + } + + /* COMPUTE_QUERY: Purpose and exact cause unknown, happens + * when you write 0x200 to 0x50c0 method 0x31c. */ + if (status & 0x00000002) { + nouveau_graph_trap_info(dev, &trap); + if (nouveau_ratelimit()) + nouveau_graph_dump_trap_info(dev, + "PGRAPH_COMPUTE_QUERY", &trap); + status &= ~0x00000002; + nv_wr32(dev, NV03_PGRAPH_INTR, 0x00000002); + } + + /* Unknown, never seen: 0x4 */ + + /* ILLEGAL_MTHD: You used a wrong method for this class. */ + if (status & 0x00000010) { + nouveau_graph_trap_info(dev, &trap); + if (nouveau_pgraph_intr_swmthd(dev, &trap)) + unhandled = 1; + if (unhandled && nouveau_ratelimit()) + nouveau_graph_dump_trap_info(dev, + "PGRAPH_ILLEGAL_MTHD", &trap); + status &= ~0x00000010; + nv_wr32(dev, NV03_PGRAPH_INTR, 0x00000010); + } + + /* ILLEGAL_CLASS: You used a wrong class. */ + if (status & 0x00000020) { + nouveau_graph_trap_info(dev, &trap); + if (nouveau_ratelimit()) + nouveau_graph_dump_trap_info(dev, + "PGRAPH_ILLEGAL_CLASS", &trap); + status &= ~0x00000020; + nv_wr32(dev, NV03_PGRAPH_INTR, 0x00000020); + } + + /* DOUBLE_NOTIFY: You tried to set a NOTIFY on another NOTIFY. */ + if (status & 0x00000040) { + nouveau_graph_trap_info(dev, &trap); + if (nouveau_ratelimit()) + nouveau_graph_dump_trap_info(dev, + "PGRAPH_DOUBLE_NOTIFY", &trap); + status &= ~0x00000040; + nv_wr32(dev, NV03_PGRAPH_INTR, 0x00000040); + } + + /* CONTEXT_SWITCH: PGRAPH needs us to load a new context */ + if (status & 0x00001000) { + nv_wr32(dev, 0x400500, 0x00000000); + nv_wr32(dev, NV03_PGRAPH_INTR, + NV_PGRAPH_INTR_CONTEXT_SWITCH); + nv_wr32(dev, NV40_PGRAPH_INTR_EN, nv_rd32(dev, + NV40_PGRAPH_INTR_EN) & + ~NV_PGRAPH_INTR_CONTEXT_SWITCH); + nv_wr32(dev, 0x400500, 0x00010001); + + nv50_graph_context_switch(dev); + + status &= ~NV_PGRAPH_INTR_CONTEXT_SWITCH; + } + + /* BUFFER_NOTIFY: Your m2mf transfer finished */ + if (status & 0x00010000) { + nouveau_graph_trap_info(dev, &trap); + if (nouveau_ratelimit()) + nouveau_graph_dump_trap_info(dev, + "PGRAPH_BUFFER_NOTIFY", &trap); + status &= ~0x00010000; + nv_wr32(dev, NV03_PGRAPH_INTR, 0x00010000); + } + + /* DATA_ERROR: Invalid value for this method, or invalid + * state in current PGRAPH context for this operation */ + if (status & 0x00100000) { + nouveau_graph_trap_info(dev, &trap); + if (nouveau_ratelimit()) { + nouveau_graph_dump_trap_info(dev, + "PGRAPH_DATA_ERROR", &trap); + NV_INFO (dev, "PGRAPH_DATA_ERROR - "); + nouveau_print_enum_names(nv_rd32(dev, 0x400110), + nv50_data_error_names); + printk("\n"); + } + status &= ~0x00100000; + nv_wr32(dev, NV03_PGRAPH_INTR, 0x00100000); + } + + /* TRAP: Something bad happened in the middle of command + * execution. Has a billion types, subtypes, and even + * subsubtypes. */ + if (status & 0x00200000) { + nv50_pgraph_trap_handler(dev); + status &= ~0x00200000; + nv_wr32(dev, NV03_PGRAPH_INTR, 0x00200000); + } + + /* Unknown, never seen: 0x00400000 */ + + /* SINGLE_STEP: Happens on every method if you turned on + * single stepping in 40008c */ + if (status & 0x01000000) { + nouveau_graph_trap_info(dev, &trap); + if (nouveau_ratelimit()) + nouveau_graph_dump_trap_info(dev, + "PGRAPH_SINGLE_STEP", &trap); + status &= ~0x01000000; + nv_wr32(dev, NV03_PGRAPH_INTR, 0x01000000); + } + + /* 0x02000000 happens when you pause a ctxprog... + * but the only way this can happen that I know is by + * poking the relevant MMIO register, and we don't + * do that. */ + + if (status) { + NV_INFO(dev, "Unhandled PGRAPH_INTR - 0x%08x\n", + status); + nv_wr32(dev, NV03_PGRAPH_INTR, status); + } + + { + const int isb = (1 << 16) | (1 << 0); + + if ((nv_rd32(dev, 0x400500) & isb) != isb) + nv_wr32(dev, 0x400500, + nv_rd32(dev, 0x400500) | isb); + } + } + + nv_wr32(dev, NV03_PMC_INTR_0, NV_PMC_INTR_0_PGRAPH_PENDING); + if (nv_rd32(dev, 0x400824) & (1 << 31)) + nv_wr32(dev, 0x400824, nv_rd32(dev, 0x400824) & ~(1 << 31)); +} +#endif + +static void +nouveau_crtc_irq_handler(struct drm_device *dev, int crtc) +{ + if (crtc & 1) + nv_wr32(dev, NV_CRTC0_INTSTAT, NV_CRTC_INTR_VBLANK); + + if (crtc & 2) + nv_wr32(dev, NV_CRTC1_INTSTAT, NV_CRTC_INTR_VBLANK); +} + +static void +nouveau_pbus_irq_handler(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t status = nv_rd32(dev, 0x1100); + uint32_t mask = (dev_priv->chipset >= 0xc0) ? 0xf : 0x8; + + if (status & mask) { + uint32_t addr = nv_rd32(dev, 0x9084); + uint32_t data = nv_rd32(dev, 0x9088); + + if (!(addr & 1)) { + NV_ERROR(dev, "PBUS: Unknown MMIO problem %06x %08x\n", addr, data); + } else if (addr & 0x2) { + NV_ERROR(dev, "PBUS: MMIO write fault, addr %06x data %08x\n", addr & ~3, data); + } else { + NV_ERROR(dev, "PBUS: MMIO read fault, addr %06x\n", addr & ~3); + } + if (status & 1) + NV_ERROR(dev, "PBUS: accessed disabled PSUBFIFO\n"); + if (status & 2) + NV_ERROR(dev, "PBUS: accessed wrong address inside unit\n"); + if (status & 4) + NV_ERROR(dev, "PBUS: accessed address is outside unit\n"); + + if (dev_priv->chipset >= 0xc0) { + nv_wr32(dev, 0x9084, 0); + nv_wr32(dev, 0x9088, 0); + } + nv_wr32(dev, 0x1100, status & mask); + status &= ~mask; + } + + if (status) { + NV_ERROR(dev, "PBUS: unknown interrupt %08x\n", status); + nv_wr32(dev, 0x1100, status); + } +} + +void nouveau_irq_register(struct drm_device *dev, int irq, nouveau_irqhandler_t handler) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + unsigned long flags; + spin_lock_irqsave(&dev_priv->irq_lock, flags); + BUG_ON(dev_priv->irq_handler[irq]); + dev_priv->irq_handler[irq] = handler; + spin_unlock_irqrestore(&dev_priv->irq_lock, flags); +} + +void nouveau_irq_unregister(struct drm_device *dev, int irq) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + unsigned long flags; + spin_lock_irqsave(&dev_priv->irq_lock, flags); + BUG_ON(!dev_priv->irq_handler[irq]); + dev_priv->irq_handler[irq] = 0; + spin_unlock_irqrestore(&dev_priv->irq_lock, flags); +} + +irqreturn_t +nouveau_irq_handler(DRM_IRQ_ARGS) +{ + struct drm_device *dev = (struct drm_device *)arg; + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t status; +#if 0 + uint32_t fbdev_flags = 0; +#endif + unsigned long flags; + int i; + + status = nv_rd32(dev, NV03_PMC_INTR_0); + if (!status) + return IRQ_NONE; + spin_lock_irqsave(&dev_priv->irq_lock, flags); + + if (status & 0x80000000) { + NV_ERROR(dev, "Got a SOFTWARE interrupt for no good reason.\n"); + nv_wr32(dev, NV03_PMC_INTR_0, 0); + status &= ~0x80000000; + } + + if (status & 0x10000000) { + nouveau_pbus_irq_handler(dev); + status &= ~0x10000000; + } + + for (i = 0; i < 32; i++) { + if (status & 1 << i) { + if (dev_priv->irq_handler[i]) { + dev_priv->irq_handler[i](dev, i); + status &= ~(1 << i); + } + } + } + +#if 0 + if (dev_priv->fbdev_info) { + fbdev_flags = dev_priv->fbdev_info->flags; + dev_priv->fbdev_info->flags |= FBINFO_HWACCEL_DISABLED; + } +#endif + + if (status & NV_PMC_INTR_0_CRTCn_PENDING) { + nouveau_crtc_irq_handler(dev, (status>>24)&3); + status &= ~NV_PMC_INTR_0_CRTCn_PENDING; + } + + if (status & (NV_PMC_INTR_0_NV50_DISPLAY_PENDING | + NV_PMC_INTR_0_NV50_I2C_PENDING)) { + nv50_display_irq_handler(dev); + status &= ~(NV_PMC_INTR_0_NV50_DISPLAY_PENDING | + NV_PMC_INTR_0_NV50_I2C_PENDING); + } + + if (status) + NV_ERROR(dev, "Unhandled PMC INTR status bits 0x%08x\n", status); + +#if 0 + if (dev_priv->fbdev_info) + dev_priv->fbdev_info->flags = fbdev_flags; +#endif + + spin_unlock_irqrestore(&dev_priv->irq_lock, flags); + + return IRQ_HANDLED; +} diff --git a/driver/pscnv/nouveau_mem.c b/driver/pscnv/nouveau_mem.c new file mode 100644 index 00000000..d3a44cf6 --- /dev/null +++ b/driver/pscnv/nouveau_mem.c @@ -0,0 +1,182 @@ +/* + * Copyright (C) The Weather Channel, Inc. 2002. All Rights Reserved. + * Copyright 2005 Stephane Marchesin + * + * The Weather Channel (TM) funded Tungsten Graphics to develop the + * initial release of the Radeon 8500 driver under the XFree86 license. + * This notice must be preserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS AND/OR THEIR SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + * + * Authors: + * Keith Whitwell + */ + + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" + +void +nouveau_mem_timing_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_memtimings *memtimings = &pm->memtimings; + struct nvbios *bios = &dev_priv->vbios; + struct bit_entry P; + u8 tUNK_0, tUNK_1, tUNK_2; + u8 tRP; /* Byte 3 */ + u8 tRAS; /* Byte 5 */ + u8 tRFC; /* Byte 7 */ + u8 tRC; /* Byte 9 */ + u8 tUNK_10, tUNK_11, tUNK_12, tUNK_13, tUNK_14; + u8 tUNK_18, tUNK_19, tUNK_20, tUNK_21; + u8 *mem = NULL, *entry; + int i, recordlen, entries; + + if (bios->type == NVBIOS_BIT) { + if (bit_table(dev, 'P', &P)) + return; + + if (P.version == 1) + mem = ROMPTR(bios, P.data[4]); + else + if (P.version == 2) + mem = ROMPTR(bios, P.data[8]); + else { + NV_WARN(dev, "unknown mem for BIT P %d\n", P.version); + } + } else { + NV_DEBUG(dev, "BMP version too old for memory\n"); + return; + } + + if (!mem) { + NV_DEBUG(dev, "memory timing table pointer invalid\n"); + return; + } + + if (mem[0] != 0x10) { + NV_WARN(dev, "memory timing table 0x%02x unknown\n", mem[0]); + return; + } + + /* validate record length */ + entries = mem[2]; + recordlen = mem[3]; + if (recordlen < 15) { + NV_ERROR(dev, "mem timing table length unknown: %d\n", mem[3]); + return; + } + + /* parse vbios entries into common format */ + memtimings->timing = + kcalloc(entries, sizeof(*memtimings->timing), GFP_KERNEL); + if (!memtimings->timing) + return; + + entry = mem + mem[1]; + for (i = 0; i < entries; i++, entry += recordlen) { + struct nouveau_pm_memtiming *timing = &pm->memtimings.timing[i]; + if (entry[0] == 0) + continue; + + tUNK_18 = 1; + tUNK_19 = 1; + tUNK_20 = 0; + tUNK_21 = 0; + switch (recordlen>22?22:recordlen) { + case 0x22: + tUNK_21 = entry[21]; + case 0x21: + tUNK_20 = entry[20]; + case 0x20: + tUNK_19 = entry[19]; + case 0x19: + tUNK_18 = entry[18]; + default: + tUNK_0 = entry[0]; + tUNK_1 = entry[1]; + tUNK_2 = entry[2]; + tRP = entry[3]; + tRAS = entry[5]; + tRFC = entry[7]; + tRC = entry[9]; + tUNK_10 = entry[10]; + tUNK_11 = entry[11]; + tUNK_12 = entry[12]; + tUNK_13 = entry[13]; + tUNK_14 = entry[14]; + break; + } + + timing->reg_100220 = (tRC << 24 | tRFC << 16 | tRAS << 8 | tRP); + + /* XXX: I don't trust the -1's and +1's... they must come + * from somewhere! */ + timing->reg_100224 = ((tUNK_0 + tUNK_19 + 1) << 24 | + tUNK_18 << 16 | + (tUNK_1 + tUNK_19 + 1) << 8 | + (tUNK_2 - 1)); + + timing->reg_100228 = (tUNK_12 << 16 | tUNK_11 << 8 | tUNK_10); + if(recordlen > 19) { + timing->reg_100228 += (tUNK_19 - 1) << 24; + } else { + timing->reg_100228 += tUNK_12 << 24; + } + + /* XXX: reg_10022c */ + + timing->reg_100230 = (tUNK_20 << 24 | tUNK_21 << 16 | + tUNK_13 << 8 | tUNK_13); + + /* XXX: +6? */ + timing->reg_100234 = (tRAS << 24 | (tUNK_19 + 6) << 8 | tRC); + if(tUNK_10 > tUNK_11) { + timing->reg_100234 += tUNK_10 << 16; + } else { + timing->reg_100234 += tUNK_11 << 16; + } + + /* XXX; reg_100238, reg_10023c */ + NV_DEBUG(dev, "Entry %d: 220: %08x %08x %08x %08x\n", i, + timing->reg_100220, timing->reg_100224, + timing->reg_100228, timing->reg_10022c); + NV_DEBUG(dev, " 230: %08x %08x %08x %08x\n", + timing->reg_100230, timing->reg_100234, + timing->reg_100238, timing->reg_10023c); + + NV_DEBUG(dev, " tUNK_14 %08x\n", tUNK_14); + } + + memtimings->nr_timing = entries; + memtimings->supported = true; +} + +void +nouveau_mem_timing_fini(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_memtimings *mem = &dev_priv->engine.pm.memtimings; + + kfree(mem->timing); +} diff --git a/driver/pscnv/nouveau_perf.c b/driver/pscnv/nouveau_perf.c new file mode 100644 index 00000000..ac62a1b8 --- /dev/null +++ b/driver/pscnv/nouveau_perf.c @@ -0,0 +1,205 @@ +/* + * Copyright 2010 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" + +#include "nouveau_drv.h" +#include "nouveau_pm.h" + +static void +legacy_perf_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + char *perf, *entry, *bmp = &bios->data[bios->offset]; + int headerlen, use_straps; + + if (bmp[5] < 0x5 || bmp[6] < 0x14) { + NV_DEBUG(dev, "BMP version too old for perf\n"); + return; + } + + perf = ROMPTR(bios, bmp[0x73]); + if (!perf) { + NV_DEBUG(dev, "No memclock table pointer found.\n"); + return; + } + + switch (perf[0]) { + case 0x12: + case 0x14: + case 0x18: + use_straps = 0; + headerlen = 1; + break; + case 0x01: + use_straps = perf[1] & 1; + headerlen = (use_straps ? 8 : 2); + break; + default: + NV_WARN(dev, "Unknown memclock table version %x.\n", perf[0]); + return; + } + + entry = perf + headerlen; + if (use_straps) + entry += (nv_rd32(dev, NV_PEXTDEV_BOOT_0) & 0x3c) >> 1; + + sprintf(pm->perflvl[0].name, "performance_level_0"); + pm->perflvl[0].memory = ROM16(entry[0]) * 20; + pm->nr_perflvl = 1; +} + +void +nouveau_perf_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nvbios *bios = &dev_priv->vbios; + struct bit_entry P; + u8 version, headerlen, recordlen, entries; + u8 *perf, *entry; + int vid, i; + + if (bios->type == NVBIOS_BIT) { + if (bit_table(dev, 'P', &P)) + return; + + if (P.version != 1 && P.version != 2) { + NV_WARN(dev, "unknown perf for BIT P %d\n", P.version); + return; + } + + perf = ROMPTR(bios, P.data[0]); + version = perf[0]; + headerlen = perf[1]; + if (version < 0x40) { + recordlen = perf[3] + (perf[4] * perf[5]); + entries = perf[2]; + } else { + recordlen = perf[2] + (perf[3] * perf[4]); + entries = perf[5]; + } + } else { + if (bios->data[bios->offset + 6] < 0x25) { + legacy_perf_init(dev); + return; + } + + perf = ROMPTR(bios, bios->data[bios->offset + 0x94]); + if (!perf) { + NV_DEBUG(dev, "perf table pointer invalid\n"); + return; + } + + version = perf[1]; + headerlen = perf[0]; + recordlen = perf[3]; + entries = perf[2]; + } + + entry = perf + headerlen; + for (i = 0; i < entries; i++) { + struct nouveau_pm_level *perflvl = &pm->perflvl[pm->nr_perflvl]; + + if (entry[0] == 0xff) { + entry += recordlen; + continue; + } + + switch (version) { + case 0x12: + case 0x13: + case 0x15: + perflvl->fanspeed = entry[55]; + perflvl->voltage = entry[56]; + perflvl->core = ROM32(entry[1]) * 10; + perflvl->memory = ROM32(entry[5]) * 20; + break; + case 0x21: + case 0x23: + case 0x24: + perflvl->fanspeed = entry[4]; + perflvl->voltage = entry[5]; + perflvl->core = ROM16(entry[6]) * 1000; + + if (dev_priv->chipset == 0x49 || + dev_priv->chipset == 0x4b) + perflvl->memory = ROM16(entry[11]) * 1000; + else + perflvl->memory = ROM16(entry[11]) * 2000; + + break; + case 0x25: + perflvl->fanspeed = entry[4]; + perflvl->voltage = entry[5]; + perflvl->core = ROM16(entry[6]) * 1000; + perflvl->shader = ROM16(entry[10]) * 1000; + perflvl->memory = ROM16(entry[12]) * 1000; + break; + case 0x30: + perflvl->memscript = ROM16(entry[2]); + case 0x35: + perflvl->fanspeed = entry[6]; + perflvl->voltage = entry[7]; + perflvl->core = ROM16(entry[8]) * 1000; + perflvl->shader = ROM16(entry[10]) * 1000; + perflvl->memory = ROM16(entry[12]) * 1000; + /*XXX: confirm on 0x35 */ + perflvl->unk05 = ROM16(entry[16]) * 1000; + break; + case 0x40: +#define subent(n) entry[perf[2] + ((n) * perf[3])] + perflvl->fanspeed = 0; /*XXX*/ + perflvl->voltage = entry[2]; + perflvl->core = (ROM16(subent(0)) & 0xfff) * 1000; + perflvl->shader = (ROM16(subent(1)) & 0xfff) * 1000; + perflvl->memory = (ROM16(subent(2)) & 0xfff) * 1000; + break; + } + + /* make sure vid is valid */ + if (pm->voltage.supported && perflvl->voltage) { + vid = nouveau_volt_vid_lookup(dev, perflvl->voltage); + if (vid < 0) { + NV_DEBUG(dev, "drop perflvl %d, bad vid\n", i); + entry += recordlen; + continue; + } + } + + snprintf(perflvl->name, sizeof(perflvl->name), + "performance_level_%d", i); + perflvl->id = i; + pm->nr_perflvl++; + + entry += recordlen; + } +} + +void +nouveau_perf_fini(struct drm_device *dev) +{ +} diff --git a/driver/pscnv/nouveau_pm.c b/driver/pscnv/nouveau_pm.c new file mode 100644 index 00000000..8ef1d5b4 --- /dev/null +++ b/driver/pscnv/nouveau_pm.c @@ -0,0 +1,548 @@ +/* + * Copyright 2010 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" + +#include "nouveau_drv.h" +#include "nouveau_pm.h" + +#ifdef CONFIG_ACPI +#include +#endif +#include +#include +#include + +static int +nouveau_pm_clock_set(struct drm_device *dev, struct nouveau_pm_level *perflvl, + u8 id, u32 khz) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + void *pre_state; + + if (khz == 0) + return 0; + + pre_state = pm->clock_pre(dev, perflvl, id, khz); + if (IS_ERR(pre_state)) + return PTR_ERR(pre_state); + + if (pre_state) + pm->clock_set(dev, pre_state); + return 0; +} + +static int +nouveau_pm_perflvl_set(struct drm_device *dev, struct nouveau_pm_level *perflvl) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + int ret; + + if (perflvl == pm->cur) + return 0; + + if (pm->voltage.supported && pm->voltage_set && perflvl->voltage) { + ret = pm->voltage_set(dev, perflvl->voltage); + if (ret) { + NV_ERROR(dev, "voltage_set %d failed: %d\n", + perflvl->voltage, ret); + } + } + + nouveau_pm_clock_set(dev, perflvl, PLL_CORE, perflvl->core); + nouveau_pm_clock_set(dev, perflvl, PLL_SHADER, perflvl->shader); + nouveau_pm_clock_set(dev, perflvl, PLL_MEMORY, perflvl->memory); + nouveau_pm_clock_set(dev, perflvl, PLL_UNK05, perflvl->unk05); + + pm->cur = perflvl; + return 0; +} + +static int +nouveau_pm_profile_set(struct drm_device *dev, const char *profile) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_level *perflvl = NULL; + + /* safety precaution, for now */ + if (nouveau_perflvl_wr != 7777) + return -EPERM; + + if (!pm->clock_set) + return -EINVAL; + + if (!strncmp(profile, "boot", 4)) + perflvl = &pm->boot; + else { + int pl = simple_strtol(profile, NULL, 10); + int i; + + for (i = 0; i < pm->nr_perflvl; i++) { + if (pm->perflvl[i].id == pl) { + perflvl = &pm->perflvl[i]; + break; + } + } + + if (!perflvl) + return -EINVAL; + } + + NV_INFO(dev, "setting performance level: %s\n", profile); + return nouveau_pm_perflvl_set(dev, perflvl); +} + +static int +nouveau_pm_perflvl_get(struct drm_device *dev, struct nouveau_pm_level *perflvl) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + int ret; + + if (!pm->clock_get) + return -EINVAL; + + memset(perflvl, 0, sizeof(*perflvl)); + + ret = pm->clock_get(dev, PLL_CORE); + if (ret > 0) + perflvl->core = ret; + + ret = pm->clock_get(dev, PLL_MEMORY); + if (ret > 0) + perflvl->memory = ret; + + ret = pm->clock_get(dev, PLL_SHADER); + if (ret > 0) + perflvl->shader = ret; + + ret = pm->clock_get(dev, PLL_UNK05); + if (ret > 0) + perflvl->unk05 = ret; + + if (pm->voltage.supported && pm->voltage_get) { + ret = pm->voltage_get(dev); + if (ret > 0) + perflvl->voltage = ret; + } + + return 0; +} + +static void +nouveau_pm_perflvl_info(struct nouveau_pm_level *perflvl, char *ptr, int len) +{ + char c[16], s[16], v[16], f[16]; + + c[0] = '\0'; + if (perflvl->core) + snprintf(c, sizeof(c), " core %dMHz", perflvl->core / 1000); + + s[0] = '\0'; + if (perflvl->shader) + snprintf(s, sizeof(s), " shader %dMHz", perflvl->shader / 1000); + + v[0] = '\0'; + if (perflvl->voltage) + snprintf(v, sizeof(v), " voltage %dmV", perflvl->voltage * 10); + + f[0] = '\0'; + if (perflvl->fanspeed) + snprintf(f, sizeof(f), " fanspeed %d%%", perflvl->fanspeed); + + snprintf(ptr, len, "memory %dMHz%s%s%s%s\n", perflvl->memory / 1000, + c, s, v, f); +} + +static ssize_t +nouveau_pm_get_perflvl_info(struct device *d, + struct device_attribute *a, char *buf) +{ + struct nouveau_pm_level *perflvl = (struct nouveau_pm_level *)a; + char *ptr = buf; + int len = PAGE_SIZE; + + snprintf(ptr, len, "%d: ", perflvl->id); + ptr += strlen(buf); + len -= strlen(buf); + + nouveau_pm_perflvl_info(perflvl, ptr, len); + return strlen(buf); +} + +static ssize_t +nouveau_pm_get_perflvl(struct device *d, struct device_attribute *a, char *buf) +{ + struct drm_device *dev = pci_get_drvdata(to_pci_dev(d)); + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_level cur; + int len = PAGE_SIZE, ret; + char *ptr = buf; + + if (!pm->cur) + snprintf(ptr, len, "setting: boot\n"); + else if (pm->cur == &pm->boot) + snprintf(ptr, len, "setting: boot\nc: "); + else + snprintf(ptr, len, "setting: static %d\nc: ", pm->cur->id); + ptr += strlen(buf); + len -= strlen(buf); + + ret = nouveau_pm_perflvl_get(dev, &cur); + if (ret == 0) + nouveau_pm_perflvl_info(&cur, ptr, len); + return strlen(buf); +} + +static ssize_t +nouveau_pm_set_perflvl(struct device *d, struct device_attribute *a, + const char *buf, size_t count) +{ + struct drm_device *dev = pci_get_drvdata(to_pci_dev(d)); + int ret; + + ret = nouveau_pm_profile_set(dev, buf); + if (ret) + return ret; + return strlen(buf); +} + +static DEVICE_ATTR(performance_level, S_IRUGO | S_IWUSR, + nouveau_pm_get_perflvl, nouveau_pm_set_perflvl); + +static int +nouveau_sysfs_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct device *d = &dev->pdev->dev; + int ret, i; + + ret = device_create_file(d, &dev_attr_performance_level); + if (ret) + return ret; + + for (i = 0; i < pm->nr_perflvl; i++) { + struct nouveau_pm_level *perflvl = &pm->perflvl[i]; + + perflvl->dev_attr.attr.name = perflvl->name; + perflvl->dev_attr.attr.mode = S_IRUGO; + perflvl->dev_attr.show = nouveau_pm_get_perflvl_info; + perflvl->dev_attr.store = NULL; + sysfs_attr_init(&perflvl->dev_attr.attr); + + ret = device_create_file(d, &perflvl->dev_attr); + if (ret) { + NV_ERROR(dev, "failed pervlvl %d sysfs: %d\n", + perflvl->id, i); + perflvl->dev_attr.attr.name = NULL; + nouveau_pm_fini(dev); + return ret; + } + } + + return 0; +} + +static void +nouveau_sysfs_fini(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct device *d = &dev->pdev->dev; + int i; + + device_remove_file(d, &dev_attr_performance_level); + for (i = 0; i < pm->nr_perflvl; i++) { + struct nouveau_pm_level *pl = &pm->perflvl[i]; + + if (!pl->dev_attr.attr.name) + break; + + device_remove_file(d, &pl->dev_attr); + } +} + +static ssize_t +nouveau_hwmon_show_temp(struct device *d, struct device_attribute *a, char *buf) +{ + struct drm_device *dev = dev_get_drvdata(d); + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + + return snprintf(buf, PAGE_SIZE, "%d\n", pm->temp_get(dev)*1000); +} +static SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO, nouveau_hwmon_show_temp, + NULL, 0); + +static ssize_t +nouveau_hwmon_max_temp(struct device *d, struct device_attribute *a, char *buf) +{ + struct drm_device *dev = dev_get_drvdata(d); + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_threshold_temp *temp = &pm->threshold_temp; + + return snprintf(buf, PAGE_SIZE, "%d\n", temp->down_clock*1000); +} +static ssize_t +nouveau_hwmon_set_max_temp(struct device *d, struct device_attribute *a, + const char *buf, size_t count) +{ + struct drm_device *dev = dev_get_drvdata(d); + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_threshold_temp *temp = &pm->threshold_temp; + long value; + + if (strict_strtol(buf, 10, &value) == -EINVAL) + return count; + + temp->down_clock = value/1000; + + nouveau_temp_safety_checks(dev); + + return count; +} +static SENSOR_DEVICE_ATTR(temp1_max, S_IRUGO | S_IWUSR, nouveau_hwmon_max_temp, + nouveau_hwmon_set_max_temp, + 0); + +static ssize_t +nouveau_hwmon_critical_temp(struct device *d, struct device_attribute *a, + char *buf) +{ + struct drm_device *dev = dev_get_drvdata(d); + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_threshold_temp *temp = &pm->threshold_temp; + + return snprintf(buf, PAGE_SIZE, "%d\n", temp->critical*1000); +} +static ssize_t +nouveau_hwmon_set_critical_temp(struct device *d, struct device_attribute *a, + const char *buf, + size_t count) +{ + struct drm_device *dev = dev_get_drvdata(d); + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_threshold_temp *temp = &pm->threshold_temp; + long value; + + if (strict_strtol(buf, 10, &value) == -EINVAL) + return count; + + temp->critical = value/1000; + + nouveau_temp_safety_checks(dev); + + return count; +} +static SENSOR_DEVICE_ATTR(temp1_crit, S_IRUGO | S_IWUSR, + nouveau_hwmon_critical_temp, + nouveau_hwmon_set_critical_temp, + 0); + +static ssize_t nouveau_hwmon_show_name(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + return sprintf(buf, "nouveau\n"); +} +static SENSOR_DEVICE_ATTR(name, S_IRUGO, nouveau_hwmon_show_name, NULL, 0); + +static ssize_t nouveau_hwmon_show_update_rate(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + return sprintf(buf, "1000\n"); +} +static SENSOR_DEVICE_ATTR(update_rate, S_IRUGO, + nouveau_hwmon_show_update_rate, + NULL, 0); + +static struct attribute *hwmon_attributes[] = { + &sensor_dev_attr_temp1_input.dev_attr.attr, + &sensor_dev_attr_temp1_max.dev_attr.attr, + &sensor_dev_attr_temp1_crit.dev_attr.attr, + &sensor_dev_attr_name.dev_attr.attr, + &sensor_dev_attr_update_rate.dev_attr.attr, + NULL +}; + +static const struct attribute_group hwmon_attrgroup = { + .attrs = hwmon_attributes, +}; + +static int +nouveau_hwmon_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct device *hwmon_dev; + int ret; + + if (!pm->temp_get) + return -ENODEV; + + hwmon_dev = hwmon_device_register(&dev->pdev->dev); + if (IS_ERR(hwmon_dev)) { + ret = PTR_ERR(hwmon_dev); + NV_ERROR(dev, + "Unable to register hwmon device: %d\n", ret); + return ret; + } + dev_set_drvdata(hwmon_dev, dev); + ret = sysfs_create_group(&hwmon_dev->kobj, + &hwmon_attrgroup); + if (ret) { + NV_ERROR(dev, + "Unable to create hwmon sysfs file: %d\n", ret); + hwmon_device_unregister(hwmon_dev); + return ret; + } + + pm->hwmon = hwmon_dev; + + return 0; +} + +static void +nouveau_hwmon_fini(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + + if (pm->hwmon) { + sysfs_remove_group(&pm->hwmon->kobj, &hwmon_attrgroup); + hwmon_device_unregister(pm->hwmon); + } +} + +#ifdef CONFIG_ACPI +static int +nouveau_pm_acpi_event(struct notifier_block *nb, unsigned long val, void *data) +{ + struct drm_nouveau_private *dev_priv = + container_of(nb, struct drm_nouveau_private, engine.pm.acpi_nb); + struct drm_device *dev = dev_priv->dev; + struct acpi_bus_event *entry = (struct acpi_bus_event *)data; + + if (strcmp(entry->device_class, "ac_adapter") == 0) { + bool ac = power_supply_is_system_supplied(); + + NV_DEBUG(dev, "power supply changed: %s\n", ac ? "AC" : "DC"); + } + + return NOTIFY_OK; +} +#endif + +int +nouveau_pm_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + char info[256]; + int ret, i; + + nouveau_volt_init(dev); + nouveau_perf_init(dev); + nouveau_temp_init(dev); + nouveau_mem_timing_init(dev); + + NV_INFO(dev, "%d available performance level(s)\n", pm->nr_perflvl); + for (i = 0; i < pm->nr_perflvl; i++) { + nouveau_pm_perflvl_info(&pm->perflvl[i], info, sizeof(info)); + NV_INFO(dev, "%d: %s", pm->perflvl[i].id, info); + } + + /* determine current ("boot") performance level */ + ret = nouveau_pm_perflvl_get(dev, &pm->boot); + if (ret == 0) { + pm->cur = &pm->boot; + + nouveau_pm_perflvl_info(&pm->boot, info, sizeof(info)); + NV_INFO(dev, "c: %s", info); + } + + /* switch performance levels now if requested */ + if (nouveau_perflvl != NULL) { + ret = nouveau_pm_profile_set(dev, nouveau_perflvl); + if (ret) { + NV_ERROR(dev, "error setting perflvl \"%s\": %d\n", + nouveau_perflvl, ret); + } + } + + nouveau_sysfs_init(dev); + nouveau_hwmon_init(dev); +#ifdef CONFIG_ACPI + pm->acpi_nb.notifier_call = nouveau_pm_acpi_event; + register_acpi_notifier(&pm->acpi_nb); +#endif + + return 0; +} + +void +nouveau_pm_fini(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + + if (pm->cur != &pm->boot) + nouveau_pm_perflvl_set(dev, &pm->boot); + + nouveau_mem_timing_fini(dev); + nouveau_temp_fini(dev); + nouveau_perf_fini(dev); + nouveau_volt_fini(dev); + +#ifdef CONFIG_ACPI + unregister_acpi_notifier(&pm->acpi_nb); +#endif + nouveau_hwmon_fini(dev); + nouveau_sysfs_fini(dev); +} + +void +nouveau_pm_resume(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_level *perflvl; + + if (pm->cur == &pm->boot) + return; + + perflvl = pm->cur; + pm->cur = &pm->boot; + nouveau_pm_perflvl_set(dev, perflvl); +} diff --git a/driver/pscnv/nouveau_pm.h b/driver/pscnv/nouveau_pm.h new file mode 100644 index 00000000..4a9838dd --- /dev/null +++ b/driver/pscnv/nouveau_pm.h @@ -0,0 +1,74 @@ +/* + * Copyright 2010 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#ifndef __NOUVEAU_PM_H__ +#define __NOUVEAU_PM_H__ + +/* nouveau_pm.c */ +int nouveau_pm_init(struct drm_device *dev); +void nouveau_pm_fini(struct drm_device *dev); +void nouveau_pm_resume(struct drm_device *dev); + +/* nouveau_volt.c */ +void nouveau_volt_init(struct drm_device *); +void nouveau_volt_fini(struct drm_device *); +int nouveau_volt_vid_lookup(struct drm_device *, int voltage); +int nouveau_volt_lvl_lookup(struct drm_device *, int vid); +int nouveau_voltage_gpio_get(struct drm_device *); +int nouveau_voltage_gpio_set(struct drm_device *, int voltage); + +/* nouveau_perf.c */ +void nouveau_perf_init(struct drm_device *); +void nouveau_perf_fini(struct drm_device *); + +/* nouveau_mem.c */ +void nouveau_mem_timing_init(struct drm_device *); +void nouveau_mem_timing_fini(struct drm_device *); + +/* nv04_pm.c */ +int nv04_pm_clock_get(struct drm_device *, u32 id); +void *nv04_pm_clock_pre(struct drm_device *, struct nouveau_pm_level *, + u32 id, int khz); +void nv04_pm_clock_set(struct drm_device *, void *); + +/* nv50_pm.c */ +int nv50_pm_clock_get(struct drm_device *, u32 id); +void *nv50_pm_clock_pre(struct drm_device *, struct nouveau_pm_level *, + u32 id, int khz); +void nv50_pm_clock_set(struct drm_device *, void *); + +/* nva3_pm.c */ +int nva3_pm_clock_get(struct drm_device *, u32 id); +void *nva3_pm_clock_pre(struct drm_device *, struct nouveau_pm_level *, + u32 id, int khz); +void nva3_pm_clock_set(struct drm_device *, void *); + +/* nouveau_temp.c */ +void nouveau_temp_init(struct drm_device *dev); +void nouveau_temp_fini(struct drm_device *dev); +void nouveau_temp_safety_checks(struct drm_device *dev); +int nv40_temp_get(struct drm_device *dev); +int nv84_temp_get(struct drm_device *dev); + +#endif diff --git a/driver/pscnv/nouveau_reg.h b/driver/pscnv/nouveau_reg.h new file mode 100644 index 00000000..1b42541c --- /dev/null +++ b/driver/pscnv/nouveau_reg.h @@ -0,0 +1,862 @@ + +#define NV04_PFB_BOOT_0 0x00100000 +# define NV04_PFB_BOOT_0_RAM_AMOUNT 0x00000003 +# define NV04_PFB_BOOT_0_RAM_AMOUNT_32MB 0x00000000 +# define NV04_PFB_BOOT_0_RAM_AMOUNT_4MB 0x00000001 +# define NV04_PFB_BOOT_0_RAM_AMOUNT_8MB 0x00000002 +# define NV04_PFB_BOOT_0_RAM_AMOUNT_16MB 0x00000003 +# define NV04_PFB_BOOT_0_RAM_WIDTH_128 0x00000004 +# define NV04_PFB_BOOT_0_RAM_TYPE 0x00000028 +# define NV04_PFB_BOOT_0_RAM_TYPE_SGRAM_8MBIT 0x00000000 +# define NV04_PFB_BOOT_0_RAM_TYPE_SGRAM_16MBIT 0x00000008 +# define NV04_PFB_BOOT_0_RAM_TYPE_SGRAM_16MBIT_4BANK 0x00000010 +# define NV04_PFB_BOOT_0_RAM_TYPE_SDRAM_16MBIT 0x00000018 +# define NV04_PFB_BOOT_0_RAM_TYPE_SDRAM_64MBIT 0x00000020 +# define NV04_PFB_BOOT_0_RAM_TYPE_SDRAM_64MBITX16 0x00000028 +# define NV04_PFB_BOOT_0_UMA_ENABLE 0x00000100 +# define NV04_PFB_BOOT_0_UMA_SIZE 0x0000f000 +#define NV04_PFB_DEBUG_0 0x00100080 +# define NV04_PFB_DEBUG_0_PAGE_MODE 0x00000001 +# define NV04_PFB_DEBUG_0_REFRESH_OFF 0x00000010 +# define NV04_PFB_DEBUG_0_REFRESH_COUNTX64 0x00003f00 +# define NV04_PFB_DEBUG_0_REFRESH_SLOW_CLK 0x00004000 +# define NV04_PFB_DEBUG_0_SAFE_MODE 0x00008000 +# define NV04_PFB_DEBUG_0_ALOM_ENABLE 0x00010000 +# define NV04_PFB_DEBUG_0_CASOE 0x00100000 +# define NV04_PFB_DEBUG_0_CKE_INVERT 0x10000000 +# define NV04_PFB_DEBUG_0_REFINC 0x20000000 +# define NV04_PFB_DEBUG_0_SAVE_POWER_OFF 0x40000000 +#define NV04_PFB_CFG0 0x00100200 +# define NV04_PFB_CFG0_SCRAMBLE 0x20000000 +#define NV04_PFB_CFG1 0x00100204 +#define NV04_PFB_FIFO_DATA 0x0010020c +# define NV10_PFB_FIFO_DATA_RAM_AMOUNT_MB_MASK 0xfff00000 +# define NV10_PFB_FIFO_DATA_RAM_AMOUNT_MB_SHIFT 20 +#define NV10_PFB_REFCTRL 0x00100210 +# define NV10_PFB_REFCTRL_VALID_1 (1 << 31) +#define NV04_PFB_PAD 0x0010021c +# define NV04_PFB_PAD_CKE_NORMAL (1 << 0) +#define NV10_PFB_TILE(i) (0x00100240 + (i*16)) +#define NV10_PFB_TILE__SIZE 8 +#define NV10_PFB_TLIMIT(i) (0x00100244 + (i*16)) +#define NV10_PFB_TSIZE(i) (0x00100248 + (i*16)) +#define NV10_PFB_TSTATUS(i) (0x0010024c + (i*16)) +#define NV04_PFB_REF 0x001002d0 +# define NV04_PFB_REF_CMD_REFRESH (1 << 0) +#define NV04_PFB_PRE 0x001002d4 +# define NV04_PFB_PRE_CMD_PRECHARGE (1 << 0) +#define NV10_PFB_CLOSE_PAGE2 0x0010033c +#define NV04_PFB_SCRAMBLE(i) (0x00100400 + 4 * (i)) +#define NV40_PFB_TILE(i) (0x00100600 + (i*16)) +#define NV40_PFB_TILE__SIZE_0 12 +#define NV40_PFB_TILE__SIZE_1 15 +#define NV40_PFB_TLIMIT(i) (0x00100604 + (i*16)) +#define NV40_PFB_TSIZE(i) (0x00100608 + (i*16)) +#define NV40_PFB_TSTATUS(i) (0x0010060c + (i*16)) +#define NV40_PFB_UNK_800 0x00100800 + +#define NV_PEXTDEV_BOOT_0 0x00101000 +#define NV_PEXTDEV_BOOT_0_RAMCFG 0x0000003c +# define NV_PEXTDEV_BOOT_0_STRAP_FP_IFACE_12BIT (8 << 12) +#define NV_PEXTDEV_BOOT_3 0x0010100c + +#define NV_RAMIN 0x00700000 + +#define NV_RAMHT_HANDLE_OFFSET 0 +#define NV_RAMHT_CONTEXT_OFFSET 4 +# define NV_RAMHT_CONTEXT_VALID (1<<31) +# define NV_RAMHT_CONTEXT_CHANNEL_SHIFT 24 +# define NV_RAMHT_CONTEXT_ENGINE_SHIFT 16 +# define NV_RAMHT_CONTEXT_ENGINE_SOFTWARE 0 +# define NV_RAMHT_CONTEXT_ENGINE_GRAPHICS 1 +# define NV_RAMHT_CONTEXT_INSTANCE_SHIFT 0 +# define NV40_RAMHT_CONTEXT_CHANNEL_SHIFT 23 +# define NV40_RAMHT_CONTEXT_ENGINE_SHIFT 20 +# define NV40_RAMHT_CONTEXT_INSTANCE_SHIFT 0 + +/* DMA object defines */ +#define NV_DMA_ACCESS_RW 0 +#define NV_DMA_ACCESS_RO 1 +#define NV_DMA_ACCESS_WO 2 +#define NV_DMA_TARGET_VIDMEM 0 +#define NV_DMA_TARGET_PCI 2 +#define NV_DMA_TARGET_AGP 3 +/* The following is not a real value used by the card, it's changed by + * nouveau_object_dma_create */ +#define NV_DMA_TARGET_PCI_NONLINEAR 8 + +/* Some object classes we care about in the drm */ +#define NV_CLASS_DMA_FROM_MEMORY 0x00000002 +#define NV_CLASS_DMA_TO_MEMORY 0x00000003 +#define NV_CLASS_NULL 0x00000030 +#define NV_CLASS_DMA_IN_MEMORY 0x0000003D + +#define NV03_USER(i) (0x00800000+(i*NV03_USER_SIZE)) +#define NV03_USER__SIZE 16 +#define NV10_USER__SIZE 32 +#define NV03_USER_SIZE 0x00010000 +#define NV03_USER_DMA_PUT(i) (0x00800040+(i*NV03_USER_SIZE)) +#define NV03_USER_DMA_PUT__SIZE 16 +#define NV10_USER_DMA_PUT__SIZE 32 +#define NV03_USER_DMA_GET(i) (0x00800044+(i*NV03_USER_SIZE)) +#define NV03_USER_DMA_GET__SIZE 16 +#define NV10_USER_DMA_GET__SIZE 32 +#define NV03_USER_REF_CNT(i) (0x00800048+(i*NV03_USER_SIZE)) +#define NV03_USER_REF_CNT__SIZE 16 +#define NV10_USER_REF_CNT__SIZE 32 + +#define NV40_USER(i) (0x00c00000+(i*NV40_USER_SIZE)) +#define NV40_USER_SIZE 0x00001000 +#define NV40_USER_DMA_PUT(i) (0x00c00040+(i*NV40_USER_SIZE)) +#define NV40_USER_DMA_PUT__SIZE 32 +#define NV40_USER_DMA_GET(i) (0x00c00044+(i*NV40_USER_SIZE)) +#define NV40_USER_DMA_GET__SIZE 32 +#define NV40_USER_REF_CNT(i) (0x00c00048+(i*NV40_USER_SIZE)) +#define NV40_USER_REF_CNT__SIZE 32 + +#define NV50_USER(i) (0x00c00000+(i*NV50_USER_SIZE)) +#define NV50_USER_SIZE 0x00002000 +#define NV50_USER_DMA_PUT(i) (0x00c00040+(i*NV50_USER_SIZE)) +#define NV50_USER_DMA_PUT__SIZE 128 +#define NV50_USER_DMA_GET(i) (0x00c00044+(i*NV50_USER_SIZE)) +#define NV50_USER_DMA_GET__SIZE 128 +#define NV50_USER_REF_CNT(i) (0x00c00048+(i*NV50_USER_SIZE)) +#define NV50_USER_REF_CNT__SIZE 128 + +#define NV03_FIFO_SIZE 0x8000UL + +#define NV03_PMC_BOOT_0 0x00000000 +#define NV03_PMC_BOOT_1 0x00000004 +#define NV03_PMC_INTR_0 0x00000100 +# define NV_PMC_INTR_0_PFIFO_PENDING (1<<8) +# define NV_PMC_INTR_0_PGRAPH_PENDING (1<<12) +# define NV_PMC_INTR_0_NV50_I2C_PENDING (1<<21) +# define NV_PMC_INTR_0_CRTC0_PENDING (1<<24) +# define NV_PMC_INTR_0_CRTC1_PENDING (1<<25) +# define NV_PMC_INTR_0_NV50_DISPLAY_PENDING (1<<26) +# define NV_PMC_INTR_0_CRTCn_PENDING (3<<24) +#define NV03_PMC_INTR_EN_0 0x00000140 +# define NV_PMC_INTR_EN_0_MASTER_ENABLE (1<<0) +#define NV03_PMC_ENABLE 0x00000200 +# define NV_PMC_ENABLE_PFIFO (1<<8) +# define NV_PMC_ENABLE_PGRAPH (1<<12) +/* Disabling the below bit breaks newer (G7X only?) mobile chipsets, + * the card will hang early on in the X init process. + */ +# define NV_PMC_ENABLE_UNK13 (1<<13) +#define NV40_PMC_GRAPH_UNITS 0x00001540 +#define NV40_PMC_BACKLIGHT 0x000015f0 +# define NV40_PMC_BACKLIGHT_MASK 0x001f0000 +#define NV40_PMC_1700 0x00001700 +#define NV40_PMC_1704 0x00001704 +#define NV40_PMC_1708 0x00001708 +#define NV40_PMC_170C 0x0000170C + +/* probably PMC ? */ +#define NV50_PUNK_BAR0_PRAMIN 0x00001700 +#define NV50_PUNK_BAR_CFG_BASE 0x00001704 +#define NV50_PUNK_BAR_CFG_BASE_VALID (1<<30) +#define NV50_PUNK_BAR1_CTXDMA 0x00001708 +#define NV50_PUNK_BAR1_CTXDMA_VALID (1<<31) +#define NV50_PUNK_BAR3_CTXDMA 0x0000170C +#define NV50_PUNK_BAR3_CTXDMA_VALID (1<<31) +#define NV50_PUNK_UNK1710 0x00001710 + +#define NV04_PBUS_PCI_NV_1 0x00001804 +#define NV04_PBUS_PCI_NV_19 0x0000184C +#define NV04_PBUS_PCI_NV_20 0x00001850 +# define NV04_PBUS_PCI_NV_20_ROM_SHADOW_DISABLED (0 << 0) +# define NV04_PBUS_PCI_NV_20_ROM_SHADOW_ENABLED (1 << 0) + +#define NV04_PTIMER_INTR_0 0x00009100 +#define NV04_PTIMER_INTR_EN_0 0x00009140 +#define NV04_PTIMER_NUMERATOR 0x00009200 +#define NV04_PTIMER_DENOMINATOR 0x00009210 +#define NV04_PTIMER_TIME_0 0x00009400 +#define NV04_PTIMER_TIME_1 0x00009410 +#define NV04_PTIMER_ALARM_0 0x00009420 + +#define NV04_PGRAPH_DEBUG_0 0x00400080 +#define NV04_PGRAPH_DEBUG_1 0x00400084 +#define NV04_PGRAPH_DEBUG_2 0x00400088 +#define NV04_PGRAPH_DEBUG_3 0x0040008c +#define NV10_PGRAPH_DEBUG_4 0x00400090 +#define NV03_PGRAPH_INTR 0x00400100 +#define NV03_PGRAPH_NSTATUS 0x00400104 +# define NV04_PGRAPH_NSTATUS_STATE_IN_USE (1<<11) +# define NV04_PGRAPH_NSTATUS_INVALID_STATE (1<<12) +# define NV04_PGRAPH_NSTATUS_BAD_ARGUMENT (1<<13) +# define NV04_PGRAPH_NSTATUS_PROTECTION_FAULT (1<<14) +# define NV10_PGRAPH_NSTATUS_STATE_IN_USE (1<<23) +# define NV10_PGRAPH_NSTATUS_INVALID_STATE (1<<24) +# define NV10_PGRAPH_NSTATUS_BAD_ARGUMENT (1<<25) +# define NV10_PGRAPH_NSTATUS_PROTECTION_FAULT (1<<26) +#define NV03_PGRAPH_NSOURCE 0x00400108 +# define NV03_PGRAPH_NSOURCE_NOTIFICATION (1<<0) +# define NV03_PGRAPH_NSOURCE_DATA_ERROR (1<<1) +# define NV03_PGRAPH_NSOURCE_PROTECTION_ERROR (1<<2) +# define NV03_PGRAPH_NSOURCE_RANGE_EXCEPTION (1<<3) +# define NV03_PGRAPH_NSOURCE_LIMIT_COLOR (1<<4) +# define NV03_PGRAPH_NSOURCE_LIMIT_ZETA (1<<5) +# define NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD (1<<6) +# define NV03_PGRAPH_NSOURCE_DMA_R_PROTECTION (1<<7) +# define NV03_PGRAPH_NSOURCE_DMA_W_PROTECTION (1<<8) +# define NV03_PGRAPH_NSOURCE_FORMAT_EXCEPTION (1<<9) +# define NV03_PGRAPH_NSOURCE_PATCH_EXCEPTION (1<<10) +# define NV03_PGRAPH_NSOURCE_STATE_INVALID (1<<11) +# define NV03_PGRAPH_NSOURCE_DOUBLE_NOTIFY (1<<12) +# define NV03_PGRAPH_NSOURCE_NOTIFY_IN_USE (1<<13) +# define NV03_PGRAPH_NSOURCE_METHOD_CNT (1<<14) +# define NV03_PGRAPH_NSOURCE_BFR_NOTIFICATION (1<<15) +# define NV03_PGRAPH_NSOURCE_DMA_VTX_PROTECTION (1<<16) +# define NV03_PGRAPH_NSOURCE_DMA_WIDTH_A (1<<17) +# define NV03_PGRAPH_NSOURCE_DMA_WIDTH_B (1<<18) +#define NV03_PGRAPH_INTR_EN 0x00400140 +#define NV40_PGRAPH_INTR_EN 0x0040013C +# define NV_PGRAPH_INTR_NOTIFY (1<<0) +# define NV_PGRAPH_INTR_MISSING_HW (1<<4) +# define NV_PGRAPH_INTR_CONTEXT_SWITCH (1<<12) +# define NV_PGRAPH_INTR_BUFFER_NOTIFY (1<<16) +# define NV_PGRAPH_INTR_ERROR (1<<20) +#define NV10_PGRAPH_CTX_CONTROL 0x00400144 +#define NV10_PGRAPH_CTX_USER 0x00400148 +#define NV10_PGRAPH_CTX_SWITCH(i) (0x0040014C + 0x4*(i)) +#define NV04_PGRAPH_CTX_SWITCH1 0x00400160 +#define NV10_PGRAPH_CTX_CACHE(i, j) (0x00400160 \ + + 0x4*(i) + 0x20*(j)) +#define NV04_PGRAPH_CTX_SWITCH2 0x00400164 +#define NV04_PGRAPH_CTX_SWITCH3 0x00400168 +#define NV04_PGRAPH_CTX_SWITCH4 0x0040016C +#define NV04_PGRAPH_CTX_CONTROL 0x00400170 +#define NV04_PGRAPH_CTX_USER 0x00400174 +#define NV04_PGRAPH_CTX_CACHE1 0x00400180 +#define NV03_PGRAPH_CTX_CONTROL 0x00400190 +#define NV03_PGRAPH_CTX_USER 0x00400194 +#define NV04_PGRAPH_CTX_CACHE2 0x004001A0 +#define NV04_PGRAPH_CTX_CACHE3 0x004001C0 +#define NV04_PGRAPH_CTX_CACHE4 0x004001E0 +#define NV40_PGRAPH_CTXCTL_0304 0x00400304 +#define NV40_PGRAPH_CTXCTL_0304_XFER_CTX 0x00000001 +#define NV40_PGRAPH_CTXCTL_UCODE_STAT 0x00400308 +#define NV40_PGRAPH_CTXCTL_UCODE_STAT_IP_MASK 0xff000000 +#define NV40_PGRAPH_CTXCTL_UCODE_STAT_IP_SHIFT 24 +#define NV40_PGRAPH_CTXCTL_UCODE_STAT_OP_MASK 0x00ffffff +#define NV40_PGRAPH_CTXCTL_0310 0x00400310 +#define NV40_PGRAPH_CTXCTL_0310_XFER_SAVE 0x00000020 +#define NV40_PGRAPH_CTXCTL_0310_XFER_LOAD 0x00000040 +#define NV40_PGRAPH_CTXCTL_030C 0x0040030c +#define NV40_PGRAPH_CTXCTL_UCODE_INDEX 0x00400324 +#define NV40_PGRAPH_CTXCTL_UCODE_DATA 0x00400328 +#define NV40_PGRAPH_CTXCTL_CUR 0x0040032c +#define NV40_PGRAPH_CTXCTL_CUR_LOADED 0x01000000 +#define NV40_PGRAPH_CTXCTL_CUR_INSTANCE 0x000FFFFF +#define NV40_PGRAPH_CTXCTL_NEXT 0x00400330 +#define NV40_PGRAPH_CTXCTL_NEXT_INSTANCE 0x000fffff +#define NV50_PGRAPH_CTXCTL_CUR 0x0040032c +#define NV50_PGRAPH_CTXCTL_CUR_LOADED 0x80000000 +#define NV50_PGRAPH_CTXCTL_CUR_INSTANCE 0x00ffffff +#define NV50_PGRAPH_CTXCTL_NEXT 0x00400330 +#define NV50_PGRAPH_CTXCTL_NEXT_INSTANCE 0x00ffffff +#define NV03_PGRAPH_ABS_X_RAM 0x00400400 +#define NV03_PGRAPH_ABS_Y_RAM 0x00400480 +#define NV03_PGRAPH_X_MISC 0x00400500 +#define NV03_PGRAPH_Y_MISC 0x00400504 +#define NV04_PGRAPH_VALID1 0x00400508 +#define NV04_PGRAPH_SOURCE_COLOR 0x0040050C +#define NV04_PGRAPH_MISC24_0 0x00400510 +#define NV03_PGRAPH_XY_LOGIC_MISC0 0x00400514 +#define NV03_PGRAPH_XY_LOGIC_MISC1 0x00400518 +#define NV03_PGRAPH_XY_LOGIC_MISC2 0x0040051C +#define NV03_PGRAPH_XY_LOGIC_MISC3 0x00400520 +#define NV03_PGRAPH_CLIPX_0 0x00400524 +#define NV03_PGRAPH_CLIPX_1 0x00400528 +#define NV03_PGRAPH_CLIPY_0 0x0040052C +#define NV03_PGRAPH_CLIPY_1 0x00400530 +#define NV03_PGRAPH_ABS_ICLIP_XMAX 0x00400534 +#define NV03_PGRAPH_ABS_ICLIP_YMAX 0x00400538 +#define NV03_PGRAPH_ABS_UCLIP_XMIN 0x0040053C +#define NV03_PGRAPH_ABS_UCLIP_YMIN 0x00400540 +#define NV03_PGRAPH_ABS_UCLIP_XMAX 0x00400544 +#define NV03_PGRAPH_ABS_UCLIP_YMAX 0x00400548 +#define NV03_PGRAPH_ABS_UCLIPA_XMIN 0x00400560 +#define NV03_PGRAPH_ABS_UCLIPA_YMIN 0x00400564 +#define NV03_PGRAPH_ABS_UCLIPA_XMAX 0x00400568 +#define NV03_PGRAPH_ABS_UCLIPA_YMAX 0x0040056C +#define NV04_PGRAPH_MISC24_1 0x00400570 +#define NV04_PGRAPH_MISC24_2 0x00400574 +#define NV04_PGRAPH_VALID2 0x00400578 +#define NV04_PGRAPH_PASSTHRU_0 0x0040057C +#define NV04_PGRAPH_PASSTHRU_1 0x00400580 +#define NV04_PGRAPH_PASSTHRU_2 0x00400584 +#define NV10_PGRAPH_DIMX_TEXTURE 0x00400588 +#define NV10_PGRAPH_WDIMX_TEXTURE 0x0040058C +#define NV04_PGRAPH_COMBINE_0_ALPHA 0x00400590 +#define NV04_PGRAPH_COMBINE_0_COLOR 0x00400594 +#define NV04_PGRAPH_COMBINE_1_ALPHA 0x00400598 +#define NV04_PGRAPH_COMBINE_1_COLOR 0x0040059C +#define NV04_PGRAPH_FORMAT_0 0x004005A8 +#define NV04_PGRAPH_FORMAT_1 0x004005AC +#define NV04_PGRAPH_FILTER_0 0x004005B0 +#define NV04_PGRAPH_FILTER_1 0x004005B4 +#define NV03_PGRAPH_MONO_COLOR0 0x00400600 +#define NV04_PGRAPH_ROP3 0x00400604 +#define NV04_PGRAPH_BETA_AND 0x00400608 +#define NV04_PGRAPH_BETA_PREMULT 0x0040060C +#define NV04_PGRAPH_LIMIT_VIOL_PIX 0x00400610 +#define NV04_PGRAPH_FORMATS 0x00400618 +#define NV10_PGRAPH_DEBUG_2 0x00400620 +#define NV04_PGRAPH_BOFFSET0 0x00400640 +#define NV04_PGRAPH_BOFFSET1 0x00400644 +#define NV04_PGRAPH_BOFFSET2 0x00400648 +#define NV04_PGRAPH_BOFFSET3 0x0040064C +#define NV04_PGRAPH_BOFFSET4 0x00400650 +#define NV04_PGRAPH_BOFFSET5 0x00400654 +#define NV04_PGRAPH_BBASE0 0x00400658 +#define NV04_PGRAPH_BBASE1 0x0040065C +#define NV04_PGRAPH_BBASE2 0x00400660 +#define NV04_PGRAPH_BBASE3 0x00400664 +#define NV04_PGRAPH_BBASE4 0x00400668 +#define NV04_PGRAPH_BBASE5 0x0040066C +#define NV04_PGRAPH_BPITCH0 0x00400670 +#define NV04_PGRAPH_BPITCH1 0x00400674 +#define NV04_PGRAPH_BPITCH2 0x00400678 +#define NV04_PGRAPH_BPITCH3 0x0040067C +#define NV04_PGRAPH_BPITCH4 0x00400680 +#define NV04_PGRAPH_BLIMIT0 0x00400684 +#define NV04_PGRAPH_BLIMIT1 0x00400688 +#define NV04_PGRAPH_BLIMIT2 0x0040068C +#define NV04_PGRAPH_BLIMIT3 0x00400690 +#define NV04_PGRAPH_BLIMIT4 0x00400694 +#define NV04_PGRAPH_BLIMIT5 0x00400698 +#define NV04_PGRAPH_BSWIZZLE2 0x0040069C +#define NV04_PGRAPH_BSWIZZLE5 0x004006A0 +#define NV03_PGRAPH_STATUS 0x004006B0 +#define NV04_PGRAPH_STATUS 0x00400700 +#define NV04_PGRAPH_TRAPPED_ADDR 0x00400704 +#define NV04_PGRAPH_TRAPPED_DATA 0x00400708 +#define NV04_PGRAPH_SURFACE 0x0040070C +#define NV10_PGRAPH_TRAPPED_DATA_HIGH 0x0040070C +#define NV04_PGRAPH_STATE 0x00400710 +#define NV10_PGRAPH_SURFACE 0x00400710 +#define NV04_PGRAPH_NOTIFY 0x00400714 +#define NV10_PGRAPH_STATE 0x00400714 +#define NV10_PGRAPH_NOTIFY 0x00400718 + +#define NV04_PGRAPH_FIFO 0x00400720 + +#define NV04_PGRAPH_BPIXEL 0x00400724 +#define NV10_PGRAPH_RDI_INDEX 0x00400750 +#define NV04_PGRAPH_FFINTFC_ST2 0x00400754 +#define NV10_PGRAPH_RDI_DATA 0x00400754 +#define NV04_PGRAPH_DMA_PITCH 0x00400760 +#define NV10_PGRAPH_FFINTFC_FIFO_PTR 0x00400760 +#define NV04_PGRAPH_DVD_COLORFMT 0x00400764 +#define NV10_PGRAPH_FFINTFC_ST2 0x00400764 +#define NV04_PGRAPH_SCALED_FORMAT 0x00400768 +#define NV10_PGRAPH_FFINTFC_ST2_DL 0x00400768 +#define NV10_PGRAPH_FFINTFC_ST2_DH 0x0040076c +#define NV10_PGRAPH_DMA_PITCH 0x00400770 +#define NV10_PGRAPH_DVD_COLORFMT 0x00400774 +#define NV10_PGRAPH_SCALED_FORMAT 0x00400778 +#define NV20_PGRAPH_CHANNEL_CTX_TABLE 0x00400780 +#define NV20_PGRAPH_CHANNEL_CTX_POINTER 0x00400784 +#define NV20_PGRAPH_CHANNEL_CTX_XFER 0x00400788 +#define NV20_PGRAPH_CHANNEL_CTX_XFER_LOAD 0x00000001 +#define NV20_PGRAPH_CHANNEL_CTX_XFER_SAVE 0x00000002 +#define NV04_PGRAPH_PATT_COLOR0 0x00400800 +#define NV04_PGRAPH_PATT_COLOR1 0x00400804 +#define NV04_PGRAPH_PATTERN 0x00400808 +#define NV04_PGRAPH_PATTERN_SHAPE 0x00400810 +#define NV04_PGRAPH_CHROMA 0x00400814 +#define NV04_PGRAPH_CONTROL0 0x00400818 +#define NV04_PGRAPH_CONTROL1 0x0040081C +#define NV04_PGRAPH_CONTROL2 0x00400820 +#define NV04_PGRAPH_BLEND 0x00400824 +#define NV04_PGRAPH_STORED_FMT 0x00400830 +#define NV04_PGRAPH_PATT_COLORRAM 0x00400900 +#define NV20_PGRAPH_TILE(i) (0x00400900 + (i*16)) +#define NV20_PGRAPH_TLIMIT(i) (0x00400904 + (i*16)) +#define NV20_PGRAPH_TSIZE(i) (0x00400908 + (i*16)) +#define NV20_PGRAPH_TSTATUS(i) (0x0040090C + (i*16)) +#define NV10_PGRAPH_TILE(i) (0x00400B00 + (i*16)) +#define NV10_PGRAPH_TLIMIT(i) (0x00400B04 + (i*16)) +#define NV10_PGRAPH_TSIZE(i) (0x00400B08 + (i*16)) +#define NV10_PGRAPH_TSTATUS(i) (0x00400B0C + (i*16)) +#define NV04_PGRAPH_U_RAM 0x00400D00 +#define NV47_PGRAPH_TILE(i) (0x00400D00 + (i*16)) +#define NV47_PGRAPH_TLIMIT(i) (0x00400D04 + (i*16)) +#define NV47_PGRAPH_TSIZE(i) (0x00400D08 + (i*16)) +#define NV47_PGRAPH_TSTATUS(i) (0x00400D0C + (i*16)) +#define NV04_PGRAPH_V_RAM 0x00400D40 +#define NV04_PGRAPH_W_RAM 0x00400D80 +#define NV10_PGRAPH_COMBINER0_IN_ALPHA 0x00400E40 +#define NV10_PGRAPH_COMBINER1_IN_ALPHA 0x00400E44 +#define NV10_PGRAPH_COMBINER0_IN_RGB 0x00400E48 +#define NV10_PGRAPH_COMBINER1_IN_RGB 0x00400E4C +#define NV10_PGRAPH_COMBINER_COLOR0 0x00400E50 +#define NV10_PGRAPH_COMBINER_COLOR1 0x00400E54 +#define NV10_PGRAPH_COMBINER0_OUT_ALPHA 0x00400E58 +#define NV10_PGRAPH_COMBINER1_OUT_ALPHA 0x00400E5C +#define NV10_PGRAPH_COMBINER0_OUT_RGB 0x00400E60 +#define NV10_PGRAPH_COMBINER1_OUT_RGB 0x00400E64 +#define NV10_PGRAPH_COMBINER_FINAL0 0x00400E68 +#define NV10_PGRAPH_COMBINER_FINAL1 0x00400E6C +#define NV10_PGRAPH_WINDOWCLIP_HORIZONTAL 0x00400F00 +#define NV10_PGRAPH_WINDOWCLIP_VERTICAL 0x00400F20 +#define NV10_PGRAPH_XFMODE0 0x00400F40 +#define NV10_PGRAPH_XFMODE1 0x00400F44 +#define NV10_PGRAPH_GLOBALSTATE0 0x00400F48 +#define NV10_PGRAPH_GLOBALSTATE1 0x00400F4C +#define NV10_PGRAPH_PIPE_ADDRESS 0x00400F50 +#define NV10_PGRAPH_PIPE_DATA 0x00400F54 +#define NV04_PGRAPH_DMA_START_0 0x00401000 +#define NV04_PGRAPH_DMA_START_1 0x00401004 +#define NV04_PGRAPH_DMA_LENGTH 0x00401008 +#define NV04_PGRAPH_DMA_MISC 0x0040100C +#define NV04_PGRAPH_DMA_DATA_0 0x00401020 +#define NV04_PGRAPH_DMA_DATA_1 0x00401024 +#define NV04_PGRAPH_DMA_RM 0x00401030 +#define NV04_PGRAPH_DMA_A_XLATE_INST 0x00401040 +#define NV04_PGRAPH_DMA_A_CONTROL 0x00401044 +#define NV04_PGRAPH_DMA_A_LIMIT 0x00401048 +#define NV04_PGRAPH_DMA_A_TLB_PTE 0x0040104C +#define NV04_PGRAPH_DMA_A_TLB_TAG 0x00401050 +#define NV04_PGRAPH_DMA_A_ADJ_OFFSET 0x00401054 +#define NV04_PGRAPH_DMA_A_OFFSET 0x00401058 +#define NV04_PGRAPH_DMA_A_SIZE 0x0040105C +#define NV04_PGRAPH_DMA_A_Y_SIZE 0x00401060 +#define NV04_PGRAPH_DMA_B_XLATE_INST 0x00401080 +#define NV04_PGRAPH_DMA_B_CONTROL 0x00401084 +#define NV04_PGRAPH_DMA_B_LIMIT 0x00401088 +#define NV04_PGRAPH_DMA_B_TLB_PTE 0x0040108C +#define NV04_PGRAPH_DMA_B_TLB_TAG 0x00401090 +#define NV04_PGRAPH_DMA_B_ADJ_OFFSET 0x00401094 +#define NV04_PGRAPH_DMA_B_OFFSET 0x00401098 +#define NV04_PGRAPH_DMA_B_SIZE 0x0040109C +#define NV04_PGRAPH_DMA_B_Y_SIZE 0x004010A0 +#define NV40_PGRAPH_TILE1(i) (0x00406900 + (i*16)) +#define NV40_PGRAPH_TLIMIT1(i) (0x00406904 + (i*16)) +#define NV40_PGRAPH_TSIZE1(i) (0x00406908 + (i*16)) +#define NV40_PGRAPH_TSTATUS1(i) (0x0040690C + (i*16)) + + +/* It's a guess that this works on NV03. Confirmed on NV04, though */ +#define NV04_PFIFO_DELAY_0 0x00002040 +#define NV04_PFIFO_DMA_TIMESLICE 0x00002044 +#define NV04_PFIFO_NEXT_CHANNEL 0x00002050 +#define NV03_PFIFO_INTR_0 0x00002100 +#define NV03_PFIFO_INTR_EN_0 0x00002140 +# define NV_PFIFO_INTR_CACHE_ERROR (1<<0) +# define NV_PFIFO_INTR_RUNOUT (1<<4) +# define NV_PFIFO_INTR_RUNOUT_OVERFLOW (1<<8) +# define NV_PFIFO_INTR_DMA_PUSHER (1<<12) +# define NV_PFIFO_INTR_DMA_PT (1<<16) +# define NV_PFIFO_INTR_SEMAPHORE (1<<20) +# define NV_PFIFO_INTR_ACQUIRE_TIMEOUT (1<<24) +#define NV03_PFIFO_RAMHT 0x00002210 +#define NV03_PFIFO_RAMFC 0x00002214 +#define NV03_PFIFO_RAMRO 0x00002218 +#define NV40_PFIFO_RAMFC 0x00002220 +#define NV03_PFIFO_CACHES 0x00002500 +#define NV04_PFIFO_MODE 0x00002504 +#define NV04_PFIFO_DMA 0x00002508 +#define NV04_PFIFO_SIZE 0x0000250c +#define NV50_PFIFO_CTX_TABLE(c) (0x2600+(c)*4) +#define NV50_PFIFO_CTX_TABLE__SIZE 128 +#define NV50_PFIFO_CTX_TABLE_CHANNEL_ENABLED (1<<31) +#define NV50_PFIFO_CTX_TABLE_UNK30_BAD (1<<30) +#define NV50_PFIFO_CTX_TABLE_INSTANCE_MASK_G80 0x0FFFFFFF +#define NV50_PFIFO_CTX_TABLE_INSTANCE_MASK_G84 0x00FFFFFF +#define NV03_PFIFO_CACHE0_PUSH0 0x00003000 +#define NV03_PFIFO_CACHE0_PULL0 0x00003040 +#define NV04_PFIFO_CACHE0_PULL0 0x00003050 +#define NV04_PFIFO_CACHE0_PULL1 0x00003054 +#define NV03_PFIFO_CACHE1_PUSH0 0x00003200 +#define NV03_PFIFO_CACHE1_PUSH1 0x00003204 +#define NV03_PFIFO_CACHE1_PUSH1_DMA (1<<8) +#define NV40_PFIFO_CACHE1_PUSH1_DMA (1<<16) +#define NV03_PFIFO_CACHE1_PUSH1_CHID_MASK 0x0000000f +#define NV10_PFIFO_CACHE1_PUSH1_CHID_MASK 0x0000001f +#define NV50_PFIFO_CACHE1_PUSH1_CHID_MASK 0x0000007f +#define NV03_PFIFO_CACHE1_PUT 0x00003210 +#define NV04_PFIFO_CACHE1_DMA_PUSH 0x00003220 +#define NV04_PFIFO_CACHE1_DMA_FETCH 0x00003224 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_8_BYTES 0x00000000 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_16_BYTES 0x00000008 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_24_BYTES 0x00000010 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_32_BYTES 0x00000018 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_40_BYTES 0x00000020 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_48_BYTES 0x00000028 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_56_BYTES 0x00000030 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_64_BYTES 0x00000038 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_72_BYTES 0x00000040 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_80_BYTES 0x00000048 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_88_BYTES 0x00000050 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_96_BYTES 0x00000058 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_104_BYTES 0x00000060 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_112_BYTES 0x00000068 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_120_BYTES 0x00000070 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_128_BYTES 0x00000078 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_136_BYTES 0x00000080 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_144_BYTES 0x00000088 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_152_BYTES 0x00000090 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_160_BYTES 0x00000098 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_168_BYTES 0x000000A0 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_176_BYTES 0x000000A8 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_184_BYTES 0x000000B0 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_192_BYTES 0x000000B8 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_200_BYTES 0x000000C0 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_208_BYTES 0x000000C8 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_216_BYTES 0x000000D0 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_224_BYTES 0x000000D8 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_232_BYTES 0x000000E0 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_240_BYTES 0x000000E8 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_248_BYTES 0x000000F0 +# define NV_PFIFO_CACHE1_DMA_FETCH_TRIG_256_BYTES 0x000000F8 +# define NV_PFIFO_CACHE1_DMA_FETCH_SIZE 0x0000E000 +# define NV_PFIFO_CACHE1_DMA_FETCH_SIZE_32_BYTES 0x00000000 +# define NV_PFIFO_CACHE1_DMA_FETCH_SIZE_64_BYTES 0x00002000 +# define NV_PFIFO_CACHE1_DMA_FETCH_SIZE_96_BYTES 0x00004000 +# define NV_PFIFO_CACHE1_DMA_FETCH_SIZE_128_BYTES 0x00006000 +# define NV_PFIFO_CACHE1_DMA_FETCH_SIZE_160_BYTES 0x00008000 +# define NV_PFIFO_CACHE1_DMA_FETCH_SIZE_192_BYTES 0x0000A000 +# define NV_PFIFO_CACHE1_DMA_FETCH_SIZE_224_BYTES 0x0000C000 +# define NV_PFIFO_CACHE1_DMA_FETCH_SIZE_256_BYTES 0x0000E000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS 0x001F0000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_0 0x00000000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_1 0x00010000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_2 0x00020000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_3 0x00030000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_4 0x00040000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_5 0x00050000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_6 0x00060000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_7 0x00070000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_8 0x00080000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_9 0x00090000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_10 0x000A0000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_11 0x000B0000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_12 0x000C0000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_13 0x000D0000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_14 0x000E0000 +# define NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_15 0x000F0000 +# define NV_PFIFO_CACHE1_ENDIAN 0x80000000 +# define NV_PFIFO_CACHE1_LITTLE_ENDIAN 0x7FFFFFFF +# define NV_PFIFO_CACHE1_BIG_ENDIAN 0x80000000 +#define NV04_PFIFO_CACHE1_DMA_STATE 0x00003228 +#define NV04_PFIFO_CACHE1_DMA_INSTANCE 0x0000322c +#define NV04_PFIFO_CACHE1_DMA_CTL 0x00003230 +#define NV04_PFIFO_CACHE1_DMA_PUT 0x00003240 +#define NV04_PFIFO_CACHE1_DMA_GET 0x00003244 +#define NV10_PFIFO_CACHE1_REF_CNT 0x00003248 +#define NV10_PFIFO_CACHE1_DMA_SUBROUTINE 0x0000324C +#define NV03_PFIFO_CACHE1_PULL0 0x00003240 +#define NV04_PFIFO_CACHE1_PULL0 0x00003250 +# define NV04_PFIFO_CACHE1_PULL0_HASH_FAILED 0x00000010 +# define NV04_PFIFO_CACHE1_PULL0_HASH_BUSY 0x00001000 +#define NV03_PFIFO_CACHE1_PULL1 0x00003250 +#define NV04_PFIFO_CACHE1_PULL1 0x00003254 +#define NV04_PFIFO_CACHE1_HASH 0x00003258 +#define NV10_PFIFO_CACHE1_ACQUIRE_TIMEOUT 0x00003260 +#define NV10_PFIFO_CACHE1_ACQUIRE_TIMESTAMP 0x00003264 +#define NV10_PFIFO_CACHE1_ACQUIRE_VALUE 0x00003268 +#define NV10_PFIFO_CACHE1_SEMAPHORE 0x0000326C +#define NV03_PFIFO_CACHE1_GET 0x00003270 +#define NV04_PFIFO_CACHE1_ENGINE 0x00003280 +#define NV04_PFIFO_CACHE1_DMA_DCOUNT 0x000032A0 +#define NV40_PFIFO_GRCTX_INSTANCE 0x000032E0 +#define NV40_PFIFO_UNK32E4 0x000032E4 +#define NV04_PFIFO_CACHE1_METHOD(i) (0x00003800+(i*8)) +#define NV04_PFIFO_CACHE1_DATA(i) (0x00003804+(i*8)) +#define NV40_PFIFO_CACHE1_METHOD(i) (0x00090000+(i*8)) +#define NV40_PFIFO_CACHE1_DATA(i) (0x00090004+(i*8)) + +#define NV_CRTC0_INTSTAT 0x00600100 +#define NV_CRTC0_INTEN 0x00600140 +#define NV_CRTC1_INTSTAT 0x00602100 +#define NV_CRTC1_INTEN 0x00602140 +# define NV_CRTC_INTR_VBLANK (1<<0) + +#define NV04_PRAMIN 0x00700000 + +/* Fifo commands. These are not regs, neither masks */ +#define NV03_FIFO_CMD_JUMP 0x20000000 +#define NV03_FIFO_CMD_JUMP_OFFSET_MASK 0x1ffffffc +#define NV03_FIFO_CMD_REWIND (NV03_FIFO_CMD_JUMP | (0 & NV03_FIFO_CMD_JUMP_OFFSET_MASK)) + +/* This is a partial import from rules-ng, a few things may be duplicated. + * Eventually we should completely import everything from rules-ng. + * For the moment check rules-ng for docs. + */ + +#define NV50_PMC 0x00000000 +#define NV50_PMC__LEN 0x1 +#define NV50_PMC__ESIZE 0x2000 +# define NV50_PMC_BOOT_0 0x00000000 +# define NV50_PMC_BOOT_0_REVISION 0x000000ff +# define NV50_PMC_BOOT_0_REVISION__SHIFT 0 +# define NV50_PMC_BOOT_0_ARCH 0x0ff00000 +# define NV50_PMC_BOOT_0_ARCH__SHIFT 20 +# define NV50_PMC_INTR_0 0x00000100 +# define NV50_PMC_INTR_0_PFIFO (1<<8) +# define NV50_PMC_INTR_0_PGRAPH (1<<12) +# define NV50_PMC_INTR_0_PTIMER (1<<20) +# define NV50_PMC_INTR_0_HOTPLUG (1<<21) +# define NV50_PMC_INTR_0_DISPLAY (1<<26) +# define NV50_PMC_INTR_EN_0 0x00000140 +# define NV50_PMC_INTR_EN_0_MASTER (1<<0) +# define NV50_PMC_INTR_EN_0_MASTER_DISABLED (0<<0) +# define NV50_PMC_INTR_EN_0_MASTER_ENABLED (1<<0) +# define NV50_PMC_ENABLE 0x00000200 +# define NV50_PMC_ENABLE_PFIFO (1<<8) +# define NV50_PMC_ENABLE_PGRAPH (1<<12) + +#define NV50_PCONNECTOR 0x0000e000 +#define NV50_PCONNECTOR__LEN 0x1 +#define NV50_PCONNECTOR__ESIZE 0x1000 +# define NV50_PCONNECTOR_HOTPLUG_INTR 0x0000e050 +# define NV50_PCONNECTOR_HOTPLUG_INTR_PLUG_I2C0 (1<<0) +# define NV50_PCONNECTOR_HOTPLUG_INTR_PLUG_I2C1 (1<<1) +# define NV50_PCONNECTOR_HOTPLUG_INTR_PLUG_I2C2 (1<<2) +# define NV50_PCONNECTOR_HOTPLUG_INTR_PLUG_I2C3 (1<<3) +# define NV50_PCONNECTOR_HOTPLUG_INTR_UNPLUG_I2C0 (1<<16) +# define NV50_PCONNECTOR_HOTPLUG_INTR_UNPLUG_I2C1 (1<<17) +# define NV50_PCONNECTOR_HOTPLUG_INTR_UNPLUG_I2C2 (1<<18) +# define NV50_PCONNECTOR_HOTPLUG_INTR_UNPLUG_I2C3 (1<<19) +# define NV50_PCONNECTOR_HOTPLUG_CTRL 0x0000e054 +# define NV50_PCONNECTOR_HOTPLUG_CTRL_PLUG_I2C0 (1<<0) +# define NV50_PCONNECTOR_HOTPLUG_CTRL_PLUG_I2C1 (1<<1) +# define NV50_PCONNECTOR_HOTPLUG_CTRL_PLUG_I2C2 (1<<2) +# define NV50_PCONNECTOR_HOTPLUG_CTRL_PLUG_I2C3 (1<<3) +# define NV50_PCONNECTOR_HOTPLUG_CTRL_UNPLUG_I2C0 (1<<16) +# define NV50_PCONNECTOR_HOTPLUG_CTRL_UNPLUG_I2C1 (1<<17) +# define NV50_PCONNECTOR_HOTPLUG_CTRL_UNPLUG_I2C2 (1<<18) +# define NV50_PCONNECTOR_HOTPLUG_CTRL_UNPLUG_I2C3 (1<<19) +# define NV50_PCONNECTOR_HOTPLUG_STATE 0x0000e104 +# define NV50_PCONNECTOR_HOTPLUG_STATE_PIN_CONNECTED_I2C0 (1<<2) +# define NV50_PCONNECTOR_HOTPLUG_STATE_PIN_CONNECTED_I2C1 (1<<6) +# define NV50_PCONNECTOR_HOTPLUG_STATE_PIN_CONNECTED_I2C2 (1<<10) +# define NV50_PCONNECTOR_HOTPLUG_STATE_PIN_CONNECTED_I2C3 (1<<14) +# define NV50_PCONNECTOR_I2C_PORT_0 0x0000e138 +# define NV50_PCONNECTOR_I2C_PORT_1 0x0000e150 +# define NV50_PCONNECTOR_I2C_PORT_2 0x0000e168 +# define NV50_PCONNECTOR_I2C_PORT_3 0x0000e180 +# define NV50_PCONNECTOR_I2C_PORT_4 0x0000e240 +# define NV50_PCONNECTOR_I2C_PORT_5 0x0000e258 + +#define NV50_AUXCH_DATA_OUT(i,n) ((n) * 4 + (i) * 0x50 + 0x0000e4c0) +#define NV50_AUXCH_DATA_OUT__SIZE 4 +#define NV50_AUXCH_DATA_IN(i,n) ((n) * 4 + (i) * 0x50 + 0x0000e4d0) +#define NV50_AUXCH_DATA_IN__SIZE 4 +#define NV50_AUXCH_ADDR(i) ((i) * 0x50 + 0x0000e4e0) +#define NV50_AUXCH_CTRL(i) ((i) * 0x50 + 0x0000e4e4) +#define NV50_AUXCH_CTRL_LINKSTAT 0x01000000 +#define NV50_AUXCH_CTRL_LINKSTAT_NOT_READY 0x00000000 +#define NV50_AUXCH_CTRL_LINKSTAT_READY 0x01000000 +#define NV50_AUXCH_CTRL_LINKEN 0x00100000 +#define NV50_AUXCH_CTRL_LINKEN_DISABLED 0x00000000 +#define NV50_AUXCH_CTRL_LINKEN_ENABLED 0x00100000 +#define NV50_AUXCH_CTRL_EXEC 0x00010000 +#define NV50_AUXCH_CTRL_EXEC_COMPLETE 0x00000000 +#define NV50_AUXCH_CTRL_EXEC_IN_PROCESS 0x00010000 +#define NV50_AUXCH_CTRL_CMD 0x0000f000 +#define NV50_AUXCH_CTRL_CMD_SHIFT 12 +#define NV50_AUXCH_CTRL_LEN 0x0000000f +#define NV50_AUXCH_CTRL_LEN_SHIFT 0 +#define NV50_AUXCH_STAT(i) ((i) * 0x50 + 0x0000e4e8) +#define NV50_AUXCH_STAT_STATE 0x10000000 +#define NV50_AUXCH_STAT_STATE_NOT_READY 0x00000000 +#define NV50_AUXCH_STAT_STATE_READY 0x10000000 +#define NV50_AUXCH_STAT_REPLY 0x000f0000 +#define NV50_AUXCH_STAT_REPLY_AUX 0x00030000 +#define NV50_AUXCH_STAT_REPLY_AUX_ACK 0x00000000 +#define NV50_AUXCH_STAT_REPLY_AUX_NACK 0x00010000 +#define NV50_AUXCH_STAT_REPLY_AUX_DEFER 0x00020000 +#define NV50_AUXCH_STAT_REPLY_I2C 0x000c0000 +#define NV50_AUXCH_STAT_REPLY_I2C_ACK 0x00000000 +#define NV50_AUXCH_STAT_REPLY_I2C_NACK 0x00040000 +#define NV50_AUXCH_STAT_REPLY_I2C_DEFER 0x00080000 +#define NV50_AUXCH_STAT_COUNT 0x0000001f + +#define NV50_PBUS 0x00088000 +#define NV50_PBUS__LEN 0x1 +#define NV50_PBUS__ESIZE 0x1000 +# define NV50_PBUS_PCI_ID 0x00088000 +# define NV50_PBUS_PCI_ID_VENDOR_ID 0x0000ffff +# define NV50_PBUS_PCI_ID_VENDOR_ID__SHIFT 0 +# define NV50_PBUS_PCI_ID_DEVICE_ID 0xffff0000 +# define NV50_PBUS_PCI_ID_DEVICE_ID__SHIFT 16 + +#define NV50_PFB 0x00100000 +#define NV50_PFB__LEN 0x1 +#define NV50_PFB__ESIZE 0x1000 + +#define NV50_PEXTDEV 0x00101000 +#define NV50_PEXTDEV__LEN 0x1 +#define NV50_PEXTDEV__ESIZE 0x1000 + +#define NV50_PROM 0x00300000 +#define NV50_PROM__LEN 0x1 +#define NV50_PROM__ESIZE 0x10000 + +#define NV50_PGRAPH 0x00400000 +#define NV50_PGRAPH__LEN 0x1 +#define NV50_PGRAPH__ESIZE 0x10000 + +#define NV50_PDISPLAY 0x00610000 +#define NV50_PDISPLAY_OBJECTS 0x00610010 +#define NV50_PDISPLAY_INTR_0 0x00610020 +#define NV50_PDISPLAY_INTR_1 0x00610024 +#define NV50_PDISPLAY_INTR_1_VBLANK_CRTC 0x0000000c +#define NV50_PDISPLAY_INTR_1_VBLANK_CRTC_SHIFT 2 +#define NV50_PDISPLAY_INTR_1_VBLANK_CRTC_(n) (1 << ((n) + 2)) +#define NV50_PDISPLAY_INTR_1_VBLANK_CRTC_0 0x00000004 +#define NV50_PDISPLAY_INTR_1_VBLANK_CRTC_1 0x00000008 +#define NV50_PDISPLAY_INTR_1_CLK_UNK10 0x00000010 +#define NV50_PDISPLAY_INTR_1_CLK_UNK20 0x00000020 +#define NV50_PDISPLAY_INTR_1_CLK_UNK40 0x00000040 +#define NV50_PDISPLAY_INTR_EN 0x0061002c +#define NV50_PDISPLAY_INTR_EN_VBLANK_CRTC 0x0000000c +#define NV50_PDISPLAY_INTR_EN_VBLANK_CRTC_(n) (1 << ((n) + 2)) +#define NV50_PDISPLAY_INTR_EN_VBLANK_CRTC_0 0x00000004 +#define NV50_PDISPLAY_INTR_EN_VBLANK_CRTC_1 0x00000008 +#define NV50_PDISPLAY_INTR_EN_CLK_UNK10 0x00000010 +#define NV50_PDISPLAY_INTR_EN_CLK_UNK20 0x00000020 +#define NV50_PDISPLAY_INTR_EN_CLK_UNK40 0x00000040 +#define NV50_PDISPLAY_UNK30_CTRL 0x00610030 +#define NV50_PDISPLAY_UNK30_CTRL_UPDATE_VCLK0 0x00000200 +#define NV50_PDISPLAY_UNK30_CTRL_UPDATE_VCLK1 0x00000400 +#define NV50_PDISPLAY_UNK30_CTRL_PENDING 0x80000000 +#define NV50_PDISPLAY_TRAPPED_ADDR 0x00610080 +#define NV50_PDISPLAY_TRAPPED_DATA 0x00610084 +#define NV50_PDISPLAY_CHANNEL_STAT(i) ((i) * 0x10 + 0x00610200) +#define NV50_PDISPLAY_CHANNEL_STAT_DMA 0x00000010 +#define NV50_PDISPLAY_CHANNEL_STAT_DMA_DISABLED 0x00000000 +#define NV50_PDISPLAY_CHANNEL_STAT_DMA_ENABLED 0x00000010 +#define NV50_PDISPLAY_CHANNEL_DMA_CB(i) ((i) * 0x10 + 0x00610204) +#define NV50_PDISPLAY_CHANNEL_DMA_CB_LOCATION 0x00000002 +#define NV50_PDISPLAY_CHANNEL_DMA_CB_LOCATION_VRAM 0x00000000 +#define NV50_PDISPLAY_CHANNEL_DMA_CB_LOCATION_SYSTEM 0x00000002 +#define NV50_PDISPLAY_CHANNEL_DMA_CB_VALID 0x00000001 +#define NV50_PDISPLAY_CHANNEL_UNK2(i) ((i) * 0x10 + 0x00610208) +#define NV50_PDISPLAY_CHANNEL_UNK3(i) ((i) * 0x10 + 0x0061020c) + +#define NV50_PDISPLAY_CURSOR 0x00610270 +#define NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i) ((i) * 0x10 + 0x00610270) +#define NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_ON 0x00000001 +#define NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS 0x00030000 +#define NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS_ACTIVE 0x00010000 + +#define NV50_PDISPLAY_CTRL_STATE 0x00610300 +#define NV50_PDISPLAY_CTRL_STATE_PENDING 0x80000000 +#define NV50_PDISPLAY_CTRL_STATE_METHOD 0x00001ffc +#define NV50_PDISPLAY_CTRL_STATE_ENABLE 0x00000001 +#define NV50_PDISPLAY_CTRL_VAL 0x00610304 +#define NV50_PDISPLAY_UNK_380 0x00610380 +#define NV50_PDISPLAY_RAM_AMOUNT 0x00610384 +#define NV50_PDISPLAY_UNK_388 0x00610388 +#define NV50_PDISPLAY_UNK_38C 0x0061038c + +#define NV50_PDISPLAY_CRTC_P(i, r) ((i) * 0x540 + NV50_PDISPLAY_CRTC_##r) +#define NV50_PDISPLAY_CRTC_C(i, r) (4 + (i) * 0x540 + NV50_PDISPLAY_CRTC_##r) +#define NV50_PDISPLAY_CRTC_UNK_0A18 /* mthd 0x0900 */ 0x00610a18 +#define NV50_PDISPLAY_CRTC_CLUT_MODE 0x00610a24 +#define NV50_PDISPLAY_CRTC_INTERLACE 0x00610a48 +#define NV50_PDISPLAY_CRTC_SCALE_CTRL 0x00610a50 +#define NV50_PDISPLAY_CRTC_CURSOR_CTRL 0x00610a58 +#define NV50_PDISPLAY_CRTC_UNK0A78 /* mthd 0x0904 */ 0x00610a78 +#define NV50_PDISPLAY_CRTC_UNK0AB8 0x00610ab8 +#define NV50_PDISPLAY_CRTC_DEPTH 0x00610ac8 +#define NV50_PDISPLAY_CRTC_CLOCK 0x00610ad0 +#define NV50_PDISPLAY_CRTC_COLOR_CTRL 0x00610ae0 +#define NV50_PDISPLAY_CRTC_SYNC_START_TO_BLANK_END 0x00610ae8 +#define NV50_PDISPLAY_CRTC_MODE_UNK1 0x00610af0 +#define NV50_PDISPLAY_CRTC_DISPLAY_TOTAL 0x00610af8 +#define NV50_PDISPLAY_CRTC_SYNC_DURATION 0x00610b00 +#define NV50_PDISPLAY_CRTC_MODE_UNK2 0x00610b08 +#define NV50_PDISPLAY_CRTC_UNK_0B10 /* mthd 0x0828 */ 0x00610b10 +#define NV50_PDISPLAY_CRTC_FB_SIZE 0x00610b18 +#define NV50_PDISPLAY_CRTC_FB_PITCH 0x00610b20 +#define NV50_PDISPLAY_CRTC_FB_PITCH_LINEAR 0x00100000 +#define NV50_PDISPLAY_CRTC_FB_POS 0x00610b28 +#define NV50_PDISPLAY_CRTC_SCALE_CENTER_OFFSET 0x00610b38 +#define NV50_PDISPLAY_CRTC_REAL_RES 0x00610b40 +#define NV50_PDISPLAY_CRTC_SCALE_RES1 0x00610b48 +#define NV50_PDISPLAY_CRTC_SCALE_RES2 0x00610b50 + +#define NV50_PDISPLAY_DAC_MODE_CTRL_P(i) (0x00610b58 + (i) * 0x8) +#define NV50_PDISPLAY_DAC_MODE_CTRL_C(i) (0x00610b5c + (i) * 0x8) +#define NV50_PDISPLAY_SOR_MODE_CTRL_P(i) (0x00610b70 + (i) * 0x8) +#define NV50_PDISPLAY_SOR_MODE_CTRL_C(i) (0x00610b74 + (i) * 0x8) +#define NV50_PDISPLAY_EXT_MODE_CTRL_P(i) (0x00610b80 + (i) * 0x8) +#define NV50_PDISPLAY_EXT_MODE_CTRL_C(i) (0x00610b84 + (i) * 0x8) +#define NV50_PDISPLAY_DAC_MODE_CTRL2_P(i) (0x00610bdc + (i) * 0x8) +#define NV50_PDISPLAY_DAC_MODE_CTRL2_C(i) (0x00610be0 + (i) * 0x8) +#define NV90_PDISPLAY_SOR_MODE_CTRL_P(i) (0x00610794 + (i) * 0x8) +#define NV90_PDISPLAY_SOR_MODE_CTRL_C(i) (0x00610798 + (i) * 0x8) + +#define NV50_PDISPLAY_CRTC_CLK 0x00614000 +#define NV50_PDISPLAY_CRTC_CLK_CTRL1(i) ((i) * 0x800 + 0x614100) +#define NV50_PDISPLAY_CRTC_CLK_CTRL1_CONNECTED 0x00000600 +#define NV50_PDISPLAY_CRTC_CLK_VPLL_A(i) ((i) * 0x800 + 0x614104) +#define NV50_PDISPLAY_CRTC_CLK_VPLL_B(i) ((i) * 0x800 + 0x614108) +#define NV50_PDISPLAY_CRTC_CLK_CTRL2(i) ((i) * 0x800 + 0x614200) + +#define NV50_PDISPLAY_DAC_CLK 0x00614000 +#define NV50_PDISPLAY_DAC_CLK_CTRL2(i) ((i) * 0x800 + 0x614280) + +#define NV50_PDISPLAY_SOR_CLK 0x00614000 +#define NV50_PDISPLAY_SOR_CLK_CTRL2(i) ((i) * 0x800 + 0x614300) + +#define NV50_PDISPLAY_VGACRTC(r) ((r) + 0x619400) + +#define NV50_PDISPLAY_DAC 0x0061a000 +#define NV50_PDISPLAY_DAC_DPMS_CTRL(i) (0x0061a004 + (i) * 0x800) +#define NV50_PDISPLAY_DAC_DPMS_CTRL_HSYNC_OFF 0x00000001 +#define NV50_PDISPLAY_DAC_DPMS_CTRL_VSYNC_OFF 0x00000004 +#define NV50_PDISPLAY_DAC_DPMS_CTRL_BLANKED 0x00000010 +#define NV50_PDISPLAY_DAC_DPMS_CTRL_OFF 0x00000040 +#define NV50_PDISPLAY_DAC_DPMS_CTRL_PENDING 0x80000000 +#define NV50_PDISPLAY_DAC_LOAD_CTRL(i) (0x0061a00c + (i) * 0x800) +#define NV50_PDISPLAY_DAC_LOAD_CTRL_ACTIVE 0x00100000 +#define NV50_PDISPLAY_DAC_LOAD_CTRL_PRESENT 0x38000000 +#define NV50_PDISPLAY_DAC_LOAD_CTRL_DONE 0x80000000 +#define NV50_PDISPLAY_DAC_CLK_CTRL1(i) (0x0061a010 + (i) * 0x800) +#define NV50_PDISPLAY_DAC_CLK_CTRL1_CONNECTED 0x00000600 + +#define NV50_PDISPLAY_SOR 0x0061c000 +#define NV50_PDISPLAY_SOR_DPMS_CTRL(i) (0x0061c004 + (i) * 0x800) +#define NV50_PDISPLAY_SOR_DPMS_CTRL_PENDING 0x80000000 +#define NV50_PDISPLAY_SOR_DPMS_CTRL_ON 0x00000001 +#define NV50_PDISPLAY_SOR_CLK_CTRL1(i) (0x0061c008 + (i) * 0x800) +#define NV50_PDISPLAY_SOR_CLK_CTRL1_CONNECTED 0x00000600 +#define NV50_PDISPLAY_SOR_DPMS_STATE(i) (0x0061c030 + (i) * 0x800) +#define NV50_PDISPLAY_SOR_DPMS_STATE_ACTIVE 0x00030000 +#define NV50_PDISPLAY_SOR_DPMS_STATE_BLANKED 0x00080000 +#define NV50_PDISPLAY_SOR_DPMS_STATE_WAIT 0x10000000 +#define NV50_PDISPLAY_SOR_BACKLIGHT 0x0061c084 +#define NV50_PDISPLAY_SOR_BACKLIGHT_ENABLE 0x80000000 +#define NV50_PDISPLAY_SOR_BACKLIGHT_LEVEL 0x00000fff +#define NV50_SOR_DP_CTRL(i,l) (0x0061c10c + (i) * 0x800 + (l) * 0x80) +#define NV50_SOR_DP_CTRL_ENABLED 0x00000001 +#define NV50_SOR_DP_CTRL_ENHANCED_FRAME_ENABLED 0x00004000 +#define NV50_SOR_DP_CTRL_LANE_MASK 0x001f0000 +#define NV50_SOR_DP_CTRL_LANE_0_ENABLED 0x00010000 +#define NV50_SOR_DP_CTRL_LANE_1_ENABLED 0x00020000 +#define NV50_SOR_DP_CTRL_LANE_2_ENABLED 0x00040000 +#define NV50_SOR_DP_CTRL_LANE_3_ENABLED 0x00080000 +#define NV50_SOR_DP_CTRL_TRAINING_PATTERN 0x0f000000 +#define NV50_SOR_DP_CTRL_TRAINING_PATTERN_DISABLED 0x00000000 +#define NV50_SOR_DP_CTRL_TRAINING_PATTERN_1 0x01000000 +#define NV50_SOR_DP_CTRL_TRAINING_PATTERN_2 0x02000000 +#define NV50_SOR_DP_UNK118(i,l) (0x0061c118 + (i) * 0x800 + (l) * 0x80) +#define NV50_SOR_DP_UNK120(i,l) (0x0061c120 + (i) * 0x800 + (l) * 0x80) +#define NV50_SOR_DP_UNK128(i,l) (0x0061c128 + (i) * 0x800 + (l) * 0x80) +#define NV50_SOR_DP_UNK130(i,l) (0x0061c130 + (i) * 0x800 + (l) * 0x80) + +#define NV50_PDISPLAY_USER(i) ((i) * 0x1000 + 0x00640000) +#define NV50_PDISPLAY_USER_PUT(i) ((i) * 0x1000 + 0x00640000) +#define NV50_PDISPLAY_USER_GET(i) ((i) * 0x1000 + 0x00640004) + +#define NV50_PDISPLAY_CURSOR_USER 0x00647000 +#define NV50_PDISPLAY_CURSOR_USER_POS_CTRL(i) ((i) * 0x1000 + 0x00647080) +#define NV50_PDISPLAY_CURSOR_USER_POS(i) ((i) * 0x1000 + 0x00647084) diff --git a/driver/pscnv/nouveau_state.c b/driver/pscnv/nouveau_state.c new file mode 100644 index 00000000..d88dbe84 --- /dev/null +++ b/driver/pscnv/nouveau_state.c @@ -0,0 +1,728 @@ +/* + * Copyright 2005 Stephane Marchesin + * Copyright 2008 Stuart Bennett + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +#include +#include +#include "drmP.h" +#include "drm.h" +#include "drm_sarea.h" +#include "drm_crtc_helper.h" +#include +#include + +#include "nouveau_drv.h" +#include "pscnv_drm.h" +#include "nouveau_reg.h" +#include "nouveau_fbcon.h" +#include "nouveau_pm.h" +#include "nv50_display.h" +#include "pscnv_vm.h" +#include "pscnv_chan.h" +#include "pscnv_fifo.h" +#include "pscnv_ioctl.h" + +static void nouveau_stub_takedown(struct drm_device *dev) {} +static int nouveau_stub_init(struct drm_device *dev) { return 0; } + +static int nouveau_init_engine_ptrs(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_engine *engine = &dev_priv->engine; + + if (dev_priv->chipset < 0x10) { + engine->gpio.init = nouveau_stub_init; + engine->gpio.takedown = nouveau_stub_takedown; + engine->gpio.get = NULL; + engine->gpio.set = NULL; + engine->gpio.irq_enable = NULL; + engine->pm.clock_get = nv04_pm_clock_get; + engine->pm.clock_pre = nv04_pm_clock_pre; + engine->pm.clock_set = nv04_pm_clock_set; + } else if (dev_priv->chipset < 0x50 || (dev_priv->chipset & 0xf0) == 0x60) { + engine->gpio.init = nouveau_stub_init; + engine->gpio.takedown = nouveau_stub_takedown; + engine->gpio.get = nv10_gpio_get; + engine->gpio.set = nv10_gpio_set; + engine->gpio.irq_enable = NULL; + engine->pm.clock_get = nv04_pm_clock_get; + engine->pm.clock_pre = nv04_pm_clock_pre; + engine->pm.clock_set = nv04_pm_clock_set; + } else { + engine->gpio.init = nv50_gpio_init; + engine->gpio.takedown = nouveau_stub_takedown; + engine->gpio.get = nv50_gpio_get; + engine->gpio.set = nv50_gpio_set; + engine->gpio.irq_enable = nv50_gpio_irq_enable; + switch (dev_priv->chipset) { + case 0xa3: + case 0xa5: + case 0xa8: + case 0xaf: + engine->pm.clock_get = nva3_pm_clock_get; + engine->pm.clock_pre = nva3_pm_clock_pre; + engine->pm.clock_set = nva3_pm_clock_set; + break; + case 0xc0: + break; + default: + engine->pm.clock_get = nv50_pm_clock_get; + engine->pm.clock_pre = nv50_pm_clock_pre; + engine->pm.clock_set = nv50_pm_clock_set; + break; + } + } + + if (dev_priv->chipset < 0x40) { + } else if (dev_priv->chipset < 0x80) { + engine->pm.temp_get = nv40_temp_get; + } else { + engine->pm.temp_get = nv84_temp_get; + } + + if (dev_priv->chipset >= 0x30 && dev_priv->chipset < 0xc0) { + engine->pm.voltage_get = nouveau_voltage_gpio_get; + engine->pm.voltage_set = nouveau_voltage_gpio_set; + } + + if (dev_priv->chipset < 0x50 || (dev_priv->chipset & 0xf0) == 0x60) { +#if 0 + engine->display.early_init = nv04_display_early_init; + engine->display.late_takedown = nv04_display_late_takedown; + engine->display.create = nv04_display_create; + engine->display.init = nv04_display_init; + engine->display.destroy = nv04_display_destroy; +#endif + NV_ERROR(dev, "NV%02x unsupported\n", dev_priv->chipset); + return -ENOSYS; + } else { + engine->display.early_init = nv50_display_early_init; + engine->display.late_takedown = nv50_display_late_takedown; + engine->display.create = nv50_display_create; + engine->display.init = nv50_display_init; + engine->display.destroy = nv50_display_destroy; + } + + return 0; +} + +static unsigned int +nouveau_vga_set_decode(void *priv, bool state) +{ + struct drm_device *dev = priv; + struct drm_nouveau_private *dev_priv = dev->dev_private; + + if (dev_priv->chipset >= 0x40) + nv_wr32(dev, 0x88054, state); + else + nv_wr32(dev, 0x1854, state); + + if (state) + return VGA_RSRC_LEGACY_IO | VGA_RSRC_LEGACY_MEM | + VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM; + else + return VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM; +} + +static void nouveau_switcheroo_set_state(struct pci_dev *pdev, + enum vga_switcheroo_state state) +{ + pm_message_t pmm = { .event = PM_EVENT_SUSPEND }; + if (state == VGA_SWITCHEROO_ON) { + printk(KERN_ERR "VGA switcheroo: switched nouveau on\n"); + nouveau_pci_resume(pdev); + } else { + printk(KERN_ERR "VGA switcheroo: switched nouveau off\n"); + nouveau_pci_suspend(pdev, pmm); + } +} + +static void nouveau_switcheroo_reprobe(struct pci_dev *pdev) +{ + struct drm_device *dev = pci_get_drvdata(pdev); + nouveau_fbcon_output_poll_changed(dev); +} + +static bool nouveau_switcheroo_can_switch(struct pci_dev *pdev) +{ + struct drm_device *dev = pci_get_drvdata(pdev); + bool can_switch; + + spin_lock(&dev->count_lock); + can_switch = (dev->open_count == 0); + spin_unlock(&dev->count_lock); + return can_switch; +} + +int +nouveau_card_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_engine *engine; + int ret; + int i; + + NV_DEBUG(dev, "prev state = %d\n", dev_priv->init_state); + + if (dev_priv->init_state == NOUVEAU_CARD_INIT_DONE) + return 0; + + NV_INFO(dev, "Initializing card...\n"); + + vga_client_register(dev->pdev, dev, NULL, nouveau_vga_set_decode); +#ifdef PSCNV_KAPI_SWITCHEROO_REPROBE + vga_switcheroo_register_client(dev->pdev, nouveau_switcheroo_set_state, + nouveau_switcheroo_can_switch); +#else + vga_switcheroo_register_client(dev->pdev, nouveau_switcheroo_set_state, + nouveau_switcheroo_reprobe, + nouveau_switcheroo_can_switch); +#endif + + dev_priv->init_state = NOUVEAU_CARD_INIT_FAILED; + + /* Initialise internal driver API hooks */ + ret = nouveau_init_engine_ptrs(dev); + if (ret) + goto out; + engine = &dev_priv->engine; + spin_lock_init(&dev_priv->irq_lock); + + /* Make the CRTCs and I2C buses accessible */ + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + ret = engine->display.early_init(dev); + if (ret) + goto out; + } + + /* Parse BIOS tables / Run init tables if card not POSTed */ + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + ret = nouveau_bios_init(dev); + if (ret) + goto out_display_early; + + nouveau_pm_init(dev); + } + + ret = pscnv_mem_init(dev); + if (ret) + goto out_bios; + + switch (dev_priv->card_type) { + case NV_50: + ret = nv50_chan_init(dev); + break; + case NV_C0: + ret = nvc0_chan_init(dev); + break; + default: + NV_ERROR(dev, "No CHAN implementation for NV%02x!\n", dev_priv->chipset); + ret = -ENOSYS; + } + if (ret) + goto out_vram; + + switch (dev_priv->card_type) { + case NV_50: + ret = nv50_vm_init(dev); + break; + case NV_C0: + ret = nvc0_vm_init(dev); + break; + default: + NV_ERROR(dev, "No VM implementation for NV%02x!\n", dev_priv->chipset); + ret = -ENOSYS; + } + if (ret) + goto out_chan; + + /* PMC */ + nv_wr32(dev, NV03_PMC_ENABLE, 0xFFFFFFFF); + + /* PBUS */ + nv_wr32(dev, 0x1100, 0xFFFFFFFF); + nv_wr32(dev, 0x1140, 0xFFFFFFFF); + + /* PGPIO */ + ret = engine->gpio.init(dev); + if (ret) + goto out_vm; + + /* PTIMER */ + ret = nv04_timer_init(dev); + if (ret) + goto out_gpio; + + /* XXX: handle noaccel */ + switch (dev_priv->card_type) { + case NV_50: + /* PFIFO */ + ret = nv50_fifo_init(dev); + if (!ret) { + /* PGRAPH */ + nv50_graph_init(dev); + } + break; + case NV_C0: + /* PFIFO */ + ret = nvc0_fifo_init(dev); + if (!ret) { + /* PGRAPH */ + ret = nvc0_graph_init(dev); + if (!ret) { + /* PCOPY0 */ + nvc0_copy_init(dev, 0); + /* PCOPY1 */ + nvc0_copy_init(dev, 1); + } + } + break; + default: + break; + } + switch (dev_priv->chipset) { + case 0x84: + case 0x86: + case 0x92: + case 0x94: + case 0x96: + case 0xa0: + nv84_crypt_init(dev); + break; + case 0x98: + case 0xaa: + case 0xac: + nv98_crypt_init(dev); + break; + } + + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + ret = engine->display.create(dev); + if (ret) + goto out_fifo; + } + + /* this call irq_preinstall, register irq handler and + * call irq_postinstall + */ + ret = drm_irq_install(dev); + if (ret) + goto out_display; + + ret = drm_vblank_init(dev, 0); + if (ret) + goto out_irq; + + /* what about PVIDEO/PCRTC/PRAMDAC etc? */ +#if 0 + if (!engine->graph.accel_blocked) { + ret = nouveau_card_init_channel(dev); + if (ret) + goto out_irq; + } +#endif + + ret = nouveau_backlight_init(dev); + if (ret) + NV_ERROR(dev, "Error %d registering backlight\n", ret); + + dev_priv->init_state = NOUVEAU_CARD_INIT_DONE; + + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + nouveau_fbcon_init(dev); + drm_kms_helper_poll_init(dev); + } + + NV_INFO(dev, "Card initialized.\n"); + return 0; + +#if 0 +out_channel: + if (dev_priv->channel) { + nouveau_channel_free(dev_priv->channel); + dev_priv->channel = NULL; + } +#endif +out_irq: + drm_irq_uninstall(dev); +out_display: + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + engine->display.destroy(dev); + } +out_fifo: + for (i = 0; i < PSCNV_ENGINES_NUM; i++) + if (dev_priv->engines[i]) { + dev_priv->engines[i]->takedown(dev_priv->engines[i]); + dev_priv->engines[i] = 0; + } + if (dev_priv->fifo) + dev_priv->fifo->takedown(dev); +out_gpio: + engine->gpio.takedown(dev); +out_vm: + nv_wr32(dev, 0x1140, 0); + dev_priv->vm->takedown(dev); +out_chan: + dev_priv->chan->takedown(dev); +out_vram: + pscnv_mem_takedown(dev); +out_bios: + nouveau_pm_fini(dev); + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + nouveau_bios_takedown(dev); + } +out_display_early: + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + engine->display.late_takedown(dev); + } +out: + vga_client_register(dev->pdev, NULL, NULL, NULL); + return ret; +} + +static void nouveau_card_takedown(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int i; + + NV_DEBUG(dev, "prev state = %d\n", dev_priv->init_state); + + if (dev_priv->init_state != NOUVEAU_CARD_INIT_DOWN) { + NV_INFO(dev, "Stopping card...\n"); + nouveau_backlight_exit(dev); + drm_irq_uninstall(dev); + for (i = 0; i < PSCNV_ENGINES_NUM; i++) + if (dev_priv->engines[i]) { + dev_priv->engines[i]->takedown(dev_priv->engines[i]); + dev_priv->engines[i] = 0; + } + if (dev_priv->fifo) + dev_priv->fifo->takedown(dev); + dev_priv->vm->takedown(dev); + dev_priv->chan->takedown(dev); + pscnv_mem_takedown(dev); + nv_wr32(dev, 0x1140, 0); + nouveau_pm_fini(dev); + nouveau_bios_takedown(dev); + + vga_client_register(dev->pdev, NULL, NULL, NULL); + + dev_priv->init_state = NOUVEAU_CARD_INIT_DOWN; + NV_INFO(dev, "Card stopped.\n"); + } +} + +/* here a client dies, release the stuff that was allocated for its + * file_priv */ +void nouveau_preclose(struct drm_device *dev, struct drm_file *file_priv) +{ + pscnv_chan_cleanup(dev, file_priv); + pscnv_vspace_cleanup(dev, file_priv); +} + +/* first module load, setup the mmio/fb mapping */ +/* KMS: we need mmio at load time, not when the first drm client opens. */ +int nouveau_firstopen(struct drm_device *dev) +{ + nouveau_card_init(dev); + return 0; +} + +/* if we have an OF card, copy vbios to RAMIN */ +static void nouveau_OF_copy_vbios_to_ramin(struct drm_device *dev) +{ +#if defined(__powerpc__) + int size, i; + const uint32_t *bios; + struct device_node *dn = pci_device_to_OF_node(dev->pdev); + if (!dn) { + NV_INFO(dev, "Unable to get the OF node\n"); + return; + } + + bios = of_get_property(dn, "NVDA,BMP", &size); + if (bios) { + for (i = 0; i < size; i += 4) + nv_wi32(dev, i, bios[i/4]); + NV_INFO(dev, "OF bios successfully copied (%d bytes)\n", size); + } else { + NV_INFO(dev, "Unable to get the OF bios\n"); + } +#endif +} + +static struct apertures_struct *nouveau_get_apertures(struct drm_device *dev) +{ + struct pci_dev *pdev = dev->pdev; + struct apertures_struct *aper = alloc_apertures(3); + if (!aper) + return NULL; + + aper->ranges[0].base = pci_resource_start(pdev, 1); + aper->ranges[0].size = pci_resource_len(pdev, 1); + aper->count = 1; + + if (pci_resource_len(pdev, 2)) { + aper->ranges[aper->count].base = pci_resource_start(pdev, 2); + aper->ranges[aper->count].size = pci_resource_len(pdev, 2); + aper->count++; + } + + if (pci_resource_len(pdev, 3)) { + aper->ranges[aper->count].base = pci_resource_start(pdev, 3); + aper->ranges[aper->count].size = pci_resource_len(pdev, 3); + aper->count++; + } + + return aper; +} + +static int nouveau_remove_conflicting_drivers(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + bool primary = false; + dev_priv->apertures = nouveau_get_apertures(dev); + if (!dev_priv->apertures) + return -ENOMEM; + +#ifdef CONFIG_X86 + primary = dev->pdev->resource[PCI_ROM_RESOURCE].flags & IORESOURCE_ROM_SHADOW; +#endif + + remove_conflicting_framebuffers(dev_priv->apertures, "nouveaufb", primary); + return 0; +} + +#include "gdev_drv.h" + +int nouveau_load(struct drm_device *dev, unsigned long flags) +{ + struct drm_nouveau_private *dev_priv; + uint32_t reg0; + resource_size_t mmio_start_offs; + + dev_priv = kzalloc(sizeof(*dev_priv), GFP_KERNEL); + if (!dev_priv) + return -ENOMEM; + dev->dev_private = dev_priv; + dev_priv->dev = dev; + + dev_priv->flags = flags/* & NOUVEAU_FLAGS*/; + dev_priv->init_state = NOUVEAU_CARD_INIT_DOWN; + + NV_DEBUG(dev, "vendor: 0x%X device: 0x%X class: 0x%X\n", + dev->pci_vendor, dev->pci_device, dev->pdev->class); + + dev_priv->wq = create_workqueue("nouveau"); + if (!dev_priv->wq) + return -EINVAL; + + /* resource 0 is mmio regs */ + /* resource 1 is linear FB */ + /* resource 2 is RAMIN (mmio regs + 0x1000000) */ + /* resource 6 is bios */ + + /* map the mmio regs */ + mmio_start_offs = pci_resource_start(dev->pdev, 0); + dev_priv->mmio = ioremap(mmio_start_offs, 0x00800000); + if (!dev_priv->mmio) { + NV_ERROR(dev, "Unable to initialize the mmio mapping. " + "Please report your setup to " DRIVER_EMAIL "\n"); + return -EINVAL; + } + NV_DEBUG(dev, "regs mapped ok at 0x%llx\n", + (unsigned long long)mmio_start_offs); + +#ifdef __BIG_ENDIAN + /* Put the card in BE mode if it's not */ + if (nv_rd32(dev, NV03_PMC_BOOT_1)) + nv_wr32(dev, NV03_PMC_BOOT_1, 0x00000001); + + DRM_MEMORYBARRIER(); +#endif + + /* Time to determine the card architecture */ + reg0 = nv_rd32(dev, NV03_PMC_BOOT_0); + + /* We're dealing with >=NV10 */ + if ((reg0 & 0x0f000000) > 0) { + /* Bit 27-20 contain the architecture in hex */ + dev_priv->chipset = (reg0 & 0xff00000) >> 20; + /* NV04 or NV05 */ + } else if ((reg0 & 0xff00fff0) == 0x20004000) { + if (reg0 & 0x00f00000) + dev_priv->chipset = 0x05; + else + dev_priv->chipset = 0x04; + } else { + dev_priv->chipset = (reg0 & 0xf0000) >> 16; + if (dev_priv->chipset < 1 || dev_priv->chipset > 3) + dev_priv->chipset = 0xff; + } + + switch (dev_priv->chipset & 0xf0) { + case 0x00: + if (dev_priv->chipset >= 4) + dev_priv->card_type = NV_04; + else + dev_priv->card_type = dev_priv->chipset; + break; + case 0x10: + case 0x20: + case 0x30: + dev_priv->card_type = dev_priv->chipset & 0xf0; + break; + case 0x40: + case 0x60: + dev_priv->card_type = NV_40; + break; + case 0x50: + case 0x80: + case 0x90: + case 0xa0: + dev_priv->card_type = NV_50; + break; + case 0xc0: + dev_priv->card_type = NV_C0; + break; + default: + NV_INFO(dev, "Unsupported chipset 0x%08x\n", reg0); + return -EINVAL; + } + + NV_INFO(dev, "Detected an NV%02x generation card (0x%08x)\n", + dev_priv->card_type, reg0); + + dev_priv->fb_size = pci_resource_len(dev->pdev, 1); + dev_priv->fb_phys = pci_resource_start(dev->pdev, 1); + dev_priv->mmio_phys = pci_resource_start(dev->pdev, 0); + + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + int ret = nouveau_remove_conflicting_drivers(dev); + if (ret) + return ret; + } + + /* map larger RAMIN aperture on NV40 cards */ + if (dev_priv->card_type >= NV_40) { + int ramin_bar = 2; + if (pci_resource_len(dev->pdev, ramin_bar) == 0) + ramin_bar = 3; + + dev_priv->ramin_size = pci_resource_len(dev->pdev, ramin_bar); + dev_priv->ramin = ioremap( + pci_resource_start(dev->pdev, ramin_bar), + dev_priv->ramin_size); + if (!dev_priv->ramin) { + NV_ERROR(dev, "Failed to init RAMIN mapping\n"); + return -ENOMEM; + } + } + + nouveau_OF_copy_vbios_to_ramin(dev); + + /* Special flags */ + if (dev->pci_device == 0x01a0) + dev_priv->flags |= NV_NFORCE; + else if (dev->pci_device == 0x01f0) + dev_priv->flags |= NV_NFORCE2; + + /* For kernel modesetting, init card now and bring up fbcon */ + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + int ret = nouveau_card_init(dev); + if (ret) + return ret; + } + + gdev_minor_init(dev); + + return 0; +} + +static void nouveau_close(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + /* In the case of an error dev_priv may not be allocated yet */ + if (dev_priv) + nouveau_card_takedown(dev); +} + +/* KMS: we need mmio at load time, not when the first drm client opens. */ +void nouveau_lastclose(struct drm_device *dev) +{ + if (drm_core_check_feature(dev, DRIVER_MODESET)) + return; + + nouveau_close(dev); +} + +int nouveau_unload(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + gdev_minor_exit(dev); + + if (drm_core_check_feature(dev, DRIVER_MODESET)) { + drm_kms_helper_poll_fini(dev); + nouveau_fbcon_fini(dev); + dev_priv->engine.display.destroy(dev); + nouveau_close(dev); + } + + iounmap(dev_priv->mmio); + iounmap(dev_priv->ramin); + + kfree(dev_priv); + dev->dev_private = NULL; + return 0; +} + +/* Wait until (value(reg) & mask) == val, up until timeout has hit */ +bool nouveau_wait_until(struct drm_device *dev, uint64_t timeout, + uint32_t reg, uint32_t mask, uint32_t val) +{ + uint64_t start = nv04_timer_read(dev); + + do { + if ((nv_rd32(dev, reg) & mask) == val) + return true; + } while (nv04_timer_read(dev) - start < timeout); + + return false; +} + +/* Wait until (value(reg) & mask) != val, up until timeout has hit. */ +bool nouveau_wait_until_neq(struct drm_device *dev, uint64_t timeout, + uint32_t reg, uint32_t mask, uint32_t val) +{ + uint64_t start = nv04_timer_read(dev); + + do { + if ((nv_rd32(dev, reg) & mask) != val) + return true; + } while (nv04_timer_read(dev) - start < timeout); + + return false; +} diff --git a/driver/pscnv/nouveau_temp.c b/driver/pscnv/nouveau_temp.c new file mode 100644 index 00000000..16bbbf1e --- /dev/null +++ b/driver/pscnv/nouveau_temp.c @@ -0,0 +1,309 @@ +/* + * Copyright 2010 PathScale inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Martin Peres + */ + +#include "drmP.h" + +#include "nouveau_drv.h" +#include "nouveau_pm.h" + +static void +nouveau_temp_vbios_parse(struct drm_device *dev, u8 *temp) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_temp_sensor_constants *sensor = &pm->sensor_constants; + struct nouveau_pm_threshold_temp *temps = &pm->threshold_temp; + int i, headerlen, recordlen, entries; + + if (!temp) { + NV_DEBUG(dev, "temperature table pointer invalid\n"); + return; + } + + /* Set the default sensor's contants */ + sensor->offset_constant = 0; + sensor->offset_mult = 1; + sensor->offset_div = 1; + sensor->slope_mult = 1; + sensor->slope_div = 1; + + /* Set the default temperature thresholds */ + temps->critical = 110; + temps->down_clock = 100; + temps->fan_boost = 90; + + /* Set the known default values to setup the temperature sensor */ + if (dev_priv->card_type >= NV_40) { + switch (dev_priv->chipset) { + case 0x43: + sensor->offset_mult = 32060; + sensor->offset_div = 1000; + sensor->slope_mult = 792; + sensor->slope_div = 1000; + break; + + case 0x44: + case 0x47: + case 0x4a: + sensor->offset_mult = 27839; + sensor->offset_div = 1000; + sensor->slope_mult = 780; + sensor->slope_div = 1000; + break; + + case 0x46: + sensor->offset_mult = -24775; + sensor->offset_div = 100; + sensor->slope_mult = 467; + sensor->slope_div = 10000; + break; + + case 0x49: + sensor->offset_mult = -25051; + sensor->offset_div = 100; + sensor->slope_mult = 458; + sensor->slope_div = 10000; + break; + + case 0x4b: + sensor->offset_mult = -24088; + sensor->offset_div = 100; + sensor->slope_mult = 442; + sensor->slope_div = 10000; + break; + + case 0x50: + sensor->offset_mult = -22749; + sensor->offset_div = 100; + sensor->slope_mult = 431; + sensor->slope_div = 10000; + break; + } + } + + headerlen = temp[1]; + recordlen = temp[2]; + entries = temp[3]; + temp = temp + headerlen; + + /* Read the entries from the table */ + for (i = 0; i < entries; i++) { + u16 value = ROM16(temp[1]); + + switch (temp[0]) { + case 0x01: + if ((value & 0x8f) == 0) + sensor->offset_constant = (value >> 9) & 0x7f; + break; + + case 0x04: + if ((value & 0xf00f) == 0xa000) /* core */ + temps->critical = (value&0x0ff0) >> 4; + break; + + case 0x07: + if ((value & 0xf00f) == 0xa000) /* core */ + temps->down_clock = (value&0x0ff0) >> 4; + break; + + case 0x08: + if ((value & 0xf00f) == 0xa000) /* core */ + temps->fan_boost = (value&0x0ff0) >> 4; + break; + + case 0x10: + sensor->offset_mult = value; + break; + + case 0x11: + sensor->offset_div = value; + break; + + case 0x12: + sensor->slope_mult = value; + break; + + case 0x13: + sensor->slope_div = value; + break; + } + temp += recordlen; + } + + nouveau_temp_safety_checks(dev); +} + +static int +nv40_sensor_setup(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_temp_sensor_constants *sensor = &pm->sensor_constants; + u32 offset = sensor->offset_mult / sensor->offset_div; + u32 sensor_calibration; + + /* set up the sensors */ + sensor_calibration = 120 - offset - sensor->offset_constant; + sensor_calibration = sensor_calibration * sensor->slope_div / + sensor->slope_mult; + + if (dev_priv->chipset >= 0x46) + sensor_calibration |= 0x80000000; + else + sensor_calibration |= 0x10000000; + + nv_wr32(dev, 0x0015b0, sensor_calibration); + + /* Wait for the sensor to update */ + msleep(5); + + /* read */ + return nv_rd32(dev, 0x0015b4) & 0x1fff; +} + +int +nv40_temp_get(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_temp_sensor_constants *sensor = &pm->sensor_constants; + int offset = sensor->offset_mult / sensor->offset_div; + int core_temp; + + if (dev_priv->chipset >= 0x50) { + core_temp = nv_rd32(dev, 0x20008); + } else { + core_temp = nv_rd32(dev, 0x0015b4) & 0x1fff; + /* Setup the sensor if the temperature is 0 */ + if (core_temp == 0) + core_temp = nv40_sensor_setup(dev); + } + + core_temp = core_temp * sensor->slope_mult / sensor->slope_div; + core_temp = core_temp + offset + sensor->offset_constant; + + return core_temp; +} + +int +nv84_temp_get(struct drm_device *dev) +{ + return nv_rd32(dev, 0x20400); +} + +void +nouveau_temp_safety_checks(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_threshold_temp *temps = &pm->threshold_temp; + + if (temps->critical > 120) + temps->critical = 120; + else if (temps->critical < 80) + temps->critical = 80; + + if (temps->down_clock > 110) + temps->down_clock = 110; + else if (temps->down_clock < 60) + temps->down_clock = 60; + + if (temps->fan_boost > 100) + temps->fan_boost = 100; + else if (temps->fan_boost < 40) + temps->fan_boost = 40; +} + +static bool +probe_monitoring_device(struct nouveau_i2c_chan *i2c, + struct i2c_board_info *info) +{ + char modalias[16] = "i2c:"; + struct i2c_client *client; + + strlcat(modalias, info->type, sizeof(modalias)); + request_module(modalias); + + client = i2c_new_device(&i2c->adapter, info); + if (!client) + return false; + + if (!client->driver || client->driver->detect(client, info)) { + i2c_unregister_device(client); + return false; + } + + return true; +} + +static void +nouveau_temp_probe_i2c(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct dcb_table *dcb = &dev_priv->vbios.dcb; + struct i2c_board_info info[] = { + { I2C_BOARD_INFO("w83l785ts", 0x2d) }, + { I2C_BOARD_INFO("w83781d", 0x2d) }, + { I2C_BOARD_INFO("f75375", 0x2e) }, + { I2C_BOARD_INFO("adt7473", 0x2e) }, + { I2C_BOARD_INFO("lm99", 0x4c) }, + { } + }; + int idx = (dcb->version >= 0x40 ? + dcb->i2c_default_indices & 0xf : 2); + + nouveau_i2c_identify(dev, "monitoring device", info, + probe_monitoring_device, idx); +} + +void +nouveau_temp_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvbios *bios = &dev_priv->vbios; + struct bit_entry P; + u8 *temp = NULL; + + if (bios->type == NVBIOS_BIT) { + if (bit_table(dev, 'P', &P)) + return; + + if (P.version == 1) + temp = ROMPTR(bios, P.data[12]); + else if (P.version == 2) + temp = ROMPTR(bios, P.data[16]); + else + NV_WARN(dev, "unknown temp for BIT P %d\n", P.version); + + nouveau_temp_vbios_parse(dev, temp); + } + + nouveau_temp_probe_i2c(dev); +} + +void +nouveau_temp_fini(struct drm_device *dev) +{ + +} diff --git a/driver/pscnv/nouveau_volt.c b/driver/pscnv/nouveau_volt.c new file mode 100644 index 00000000..04fdc00a --- /dev/null +++ b/driver/pscnv/nouveau_volt.c @@ -0,0 +1,212 @@ +/* + * Copyright 2010 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" + +#include "nouveau_drv.h" +#include "nouveau_pm.h" + +static const enum dcb_gpio_tag vidtag[] = { 0x04, 0x05, 0x06, 0x1a }; +static int nr_vidtag = sizeof(vidtag) / sizeof(vidtag[0]); + +int +nouveau_voltage_gpio_get(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_gpio_engine *gpio = &dev_priv->engine.gpio; + struct nouveau_pm_voltage *volt = &dev_priv->engine.pm.voltage; + u8 vid = 0; + int i; + + for (i = 0; i < nr_vidtag; i++) { + if (!(volt->vid_mask & (1 << i))) + continue; + + vid |= gpio->get(dev, vidtag[i]) << i; + } + + return nouveau_volt_lvl_lookup(dev, vid); +} + +int +nouveau_voltage_gpio_set(struct drm_device *dev, int voltage) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_gpio_engine *gpio = &dev_priv->engine.gpio; + struct nouveau_pm_voltage *volt = &dev_priv->engine.pm.voltage; + int vid, i; + + vid = nouveau_volt_vid_lookup(dev, voltage); + if (vid < 0) + return vid; + + for (i = 0; i < nr_vidtag; i++) { + if (!(volt->vid_mask & (1 << i))) + continue; + + gpio->set(dev, vidtag[i], !!(vid & (1 << i))); + } + + return 0; +} + +int +nouveau_volt_vid_lookup(struct drm_device *dev, int voltage) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_voltage *volt = &dev_priv->engine.pm.voltage; + int i; + + for (i = 0; i < volt->nr_level; i++) { + if (volt->level[i].voltage == voltage) + return volt->level[i].vid; + } + + return -ENOENT; +} + +int +nouveau_volt_lvl_lookup(struct drm_device *dev, int vid) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_voltage *volt = &dev_priv->engine.pm.voltage; + int i; + + for (i = 0; i < volt->nr_level; i++) { + if (volt->level[i].vid == vid) + return volt->level[i].voltage; + } + + return -ENOENT; +} + +void +nouveau_volt_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_engine *pm = &dev_priv->engine.pm; + struct nouveau_pm_voltage *voltage = &pm->voltage; + struct nvbios *bios = &dev_priv->vbios; + struct bit_entry P; + u8 *volt = NULL, *entry; + int i, headerlen, recordlen, entries, vidmask, vidshift; + + if (bios->type == NVBIOS_BIT) { + if (bit_table(dev, 'P', &P)) + return; + + if (P.version == 1) + volt = ROMPTR(bios, P.data[16]); + else + if (P.version == 2) + volt = ROMPTR(bios, P.data[12]); + else { + NV_WARN(dev, "unknown volt for BIT P %d\n", P.version); + } + } else { + if (bios->data[bios->offset + 6] < 0x27) { + NV_DEBUG(dev, "BMP version too old for voltage\n"); + return; + } + + volt = ROMPTR(bios, bios->data[bios->offset + 0x98]); + } + + if (!volt) { + NV_DEBUG(dev, "voltage table pointer invalid\n"); + return; + } + + switch (volt[0]) { + case 0x10: + case 0x11: + case 0x12: + headerlen = 5; + recordlen = volt[1]; + entries = volt[2]; + vidshift = 0; + vidmask = volt[4]; + break; + case 0x20: + headerlen = volt[1]; + recordlen = volt[3]; + entries = volt[2]; + vidshift = 0; /* could be vidshift like 0x30? */ + vidmask = volt[5]; + break; + case 0x30: + headerlen = volt[1]; + recordlen = volt[2]; + entries = volt[3]; + vidshift = hweight8(volt[5]); + vidmask = volt[4]; + break; + default: + NV_WARN(dev, "voltage table 0x%02x unknown\n", volt[0]); + return; + } + + /* validate vid mask */ + voltage->vid_mask = vidmask; + if (!voltage->vid_mask) + return; + + i = 0; + while (vidmask) { + if (i > nr_vidtag) { + NV_DEBUG(dev, "vid bit %d unknown\n", i); + return; + } + + if (!nouveau_bios_gpio_entry(dev, vidtag[i])) { + NV_DEBUG(dev, "vid bit %d has no gpio tag\n", i); + return; + } + + vidmask >>= 1; + i++; + } + + /* parse vbios entries into common format */ + voltage->level = kcalloc(entries, sizeof(*voltage->level), GFP_KERNEL); + if (!voltage->level) + return; + + entry = volt + headerlen; + for (i = 0; i < entries; i++, entry += recordlen) { + voltage->level[i].voltage = entry[0]; + voltage->level[i].vid = entry[1] >> vidshift; + } + voltage->nr_level = entries; + voltage->supported = true; +} + +void +nouveau_volt_fini(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_pm_voltage *volt = &dev_priv->engine.pm.voltage; + + kfree(volt->level); +} diff --git a/driver/pscnv/nv04_dac.c b/driver/pscnv/nv04_dac.c new file mode 100644 index 00000000..ba6423f2 --- /dev/null +++ b/driver/pscnv/nv04_dac.c @@ -0,0 +1,544 @@ +/* + * Copyright 2003 NVIDIA, Corporation + * Copyright 2006 Dave Airlie + * Copyright 2007 Maarten Maathuis + * Copyright 2007-2009 Stuart Bennett + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +#include "drmP.h" +#include "drm_crtc_helper.h" + +#include "nouveau_drv.h" +#include "nouveau_encoder.h" +#include "nouveau_connector.h" +#include "nouveau_crtc.h" +#include "nouveau_hw.h" +#include "nvreg.h" + +int nv04_dac_output_offset(struct drm_encoder *encoder) +{ + struct dcb_entry *dcb = nouveau_encoder(encoder)->dcb; + int offset = 0; + + if (dcb->or & (8 | OUTPUT_C)) + offset += 0x68; + if (dcb->or & (8 | OUTPUT_B)) + offset += 0x2000; + + return offset; +} + +/* + * arbitrary limit to number of sense oscillations tolerated in one sample + * period (observed to be at least 13 in "nvidia") + */ +#define MAX_HBLANK_OSC 20 + +/* + * arbitrary limit to number of conflicting sample pairs to tolerate at a + * voltage step (observed to be at least 5 in "nvidia") + */ +#define MAX_SAMPLE_PAIRS 10 + +static int sample_load_twice(struct drm_device *dev, bool sense[2]) +{ + int i; + + for (i = 0; i < 2; i++) { + bool sense_a, sense_b, sense_b_prime; + int j = 0; + + /* + * wait for bit 0 clear -- out of hblank -- (say reg value 0x4), + * then wait for transition 0x4->0x5->0x4: enter hblank, leave + * hblank again + * use a 10ms timeout (guards against crtc being inactive, in + * which case blank state would never change) + */ + if (!nouveau_wait_until(dev, 10000000, NV_PRMCIO_INP0__COLOR, + 0x00000001, 0x00000000)) + return -EBUSY; + if (!nouveau_wait_until(dev, 10000000, NV_PRMCIO_INP0__COLOR, + 0x00000001, 0x00000001)) + return -EBUSY; + if (!nouveau_wait_until(dev, 10000000, NV_PRMCIO_INP0__COLOR, + 0x00000001, 0x00000000)) + return -EBUSY; + + udelay(100); + /* when level triggers, sense is _LO_ */ + sense_a = nv_rd08(dev, NV_PRMCIO_INP0) & 0x10; + + /* take another reading until it agrees with sense_a... */ + do { + udelay(100); + sense_b = nv_rd08(dev, NV_PRMCIO_INP0) & 0x10; + if (sense_a != sense_b) { + sense_b_prime = + nv_rd08(dev, NV_PRMCIO_INP0) & 0x10; + if (sense_b == sense_b_prime) { + /* ... unless two consecutive subsequent + * samples agree; sense_a is replaced */ + sense_a = sense_b; + /* force mis-match so we loop */ + sense_b = !sense_a; + } + } + } while ((sense_a != sense_b) && ++j < MAX_HBLANK_OSC); + + if (j == MAX_HBLANK_OSC) + /* with so much oscillation, default to sense:LO */ + sense[i] = false; + else + sense[i] = sense_a; + } + + return 0; +} + +static enum drm_connector_status nv04_dac_detect(struct drm_encoder *encoder, + struct drm_connector *connector) +{ + struct drm_device *dev = encoder->dev; + uint8_t saved_seq1, saved_pi, saved_rpc1, saved_cr_mode; + uint8_t saved_palette0[3], saved_palette_mask; + uint32_t saved_rtest_ctrl, saved_rgen_ctrl; + int i; + uint8_t blue; + bool sense = true; + + /* + * for this detection to work, there needs to be a mode set up on the + * CRTC. this is presumed to be the case + */ + + if (nv_two_heads(dev)) + /* only implemented for head A for now */ + NVSetOwner(dev, 0); + + saved_cr_mode = NVReadVgaCrtc(dev, 0, NV_CIO_CR_MODE_INDEX); + NVWriteVgaCrtc(dev, 0, NV_CIO_CR_MODE_INDEX, saved_cr_mode | 0x80); + + saved_seq1 = NVReadVgaSeq(dev, 0, NV_VIO_SR_CLOCK_INDEX); + NVWriteVgaSeq(dev, 0, NV_VIO_SR_CLOCK_INDEX, saved_seq1 & ~0x20); + + saved_rtest_ctrl = NVReadRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL); + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL, + saved_rtest_ctrl & ~NV_PRAMDAC_TEST_CONTROL_PWRDWN_DAC_OFF); + + msleep(10); + + saved_pi = NVReadVgaCrtc(dev, 0, NV_CIO_CRE_PIXEL_INDEX); + NVWriteVgaCrtc(dev, 0, NV_CIO_CRE_PIXEL_INDEX, + saved_pi & ~(0x80 | MASK(NV_CIO_CRE_PIXEL_FORMAT))); + saved_rpc1 = NVReadVgaCrtc(dev, 0, NV_CIO_CRE_RPC1_INDEX); + NVWriteVgaCrtc(dev, 0, NV_CIO_CRE_RPC1_INDEX, saved_rpc1 & ~0xc0); + + nv_wr08(dev, NV_PRMDIO_READ_MODE_ADDRESS, 0x0); + for (i = 0; i < 3; i++) + saved_palette0[i] = nv_rd08(dev, NV_PRMDIO_PALETTE_DATA); + saved_palette_mask = nv_rd08(dev, NV_PRMDIO_PIXEL_MASK); + nv_wr08(dev, NV_PRMDIO_PIXEL_MASK, 0); + + saved_rgen_ctrl = NVReadRAMDAC(dev, 0, NV_PRAMDAC_GENERAL_CONTROL); + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_GENERAL_CONTROL, + (saved_rgen_ctrl & ~(NV_PRAMDAC_GENERAL_CONTROL_BPC_8BITS | + NV_PRAMDAC_GENERAL_CONTROL_TERMINATION_75OHM)) | + NV_PRAMDAC_GENERAL_CONTROL_PIXMIX_ON); + + blue = 8; /* start of test range */ + + do { + bool sense_pair[2]; + + nv_wr08(dev, NV_PRMDIO_WRITE_MODE_ADDRESS, 0); + nv_wr08(dev, NV_PRMDIO_PALETTE_DATA, 0); + nv_wr08(dev, NV_PRMDIO_PALETTE_DATA, 0); + /* testing blue won't find monochrome monitors. I don't care */ + nv_wr08(dev, NV_PRMDIO_PALETTE_DATA, blue); + + i = 0; + /* take sample pairs until both samples in the pair agree */ + do { + if (sample_load_twice(dev, sense_pair)) + goto out; + } while ((sense_pair[0] != sense_pair[1]) && + ++i < MAX_SAMPLE_PAIRS); + + if (i == MAX_SAMPLE_PAIRS) + /* too much oscillation defaults to LO */ + sense = false; + else + sense = sense_pair[0]; + + /* + * if sense goes LO before blue ramps to 0x18, monitor is not connected. + * ergo, if blue gets to 0x18, monitor must be connected + */ + } while (++blue < 0x18 && sense); + +out: + nv_wr08(dev, NV_PRMDIO_PIXEL_MASK, saved_palette_mask); + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_GENERAL_CONTROL, saved_rgen_ctrl); + nv_wr08(dev, NV_PRMDIO_WRITE_MODE_ADDRESS, 0); + for (i = 0; i < 3; i++) + nv_wr08(dev, NV_PRMDIO_PALETTE_DATA, saved_palette0[i]); + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL, saved_rtest_ctrl); + NVWriteVgaCrtc(dev, 0, NV_CIO_CRE_PIXEL_INDEX, saved_pi); + NVWriteVgaCrtc(dev, 0, NV_CIO_CRE_RPC1_INDEX, saved_rpc1); + NVWriteVgaSeq(dev, 0, NV_VIO_SR_CLOCK_INDEX, saved_seq1); + NVWriteVgaCrtc(dev, 0, NV_CIO_CR_MODE_INDEX, saved_cr_mode); + + if (blue == 0x18) { + NV_INFO(dev, "Load detected on head A\n"); + return connector_status_connected; + } + + return connector_status_disconnected; +} + +uint32_t nv17_dac_sample_load(struct drm_encoder *encoder) +{ + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_gpio_engine *gpio = &dev_priv->engine.gpio; + struct dcb_entry *dcb = nouveau_encoder(encoder)->dcb; + uint32_t sample, testval, regoffset = nv04_dac_output_offset(encoder); + uint32_t saved_powerctrl_2 = 0, saved_powerctrl_4 = 0, saved_routput, + saved_rtest_ctrl, saved_gpio0, saved_gpio1, temp, routput; + int head; + +#define RGB_TEST_DATA(r, g, b) (r << 0 | g << 10 | b << 20) + if (dcb->type == OUTPUT_TV) { + testval = RGB_TEST_DATA(0xa0, 0xa0, 0xa0); + + if (dev_priv->vbios.tvdactestval) + testval = dev_priv->vbios.tvdactestval; + } else { + testval = RGB_TEST_DATA(0x140, 0x140, 0x140); /* 0x94050140 */ + + if (dev_priv->vbios.dactestval) + testval = dev_priv->vbios.dactestval; + } + + saved_rtest_ctrl = NVReadRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL + regoffset); + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL + regoffset, + saved_rtest_ctrl & ~NV_PRAMDAC_TEST_CONTROL_PWRDWN_DAC_OFF); + + saved_powerctrl_2 = nvReadMC(dev, NV_PBUS_POWERCTRL_2); + + nvWriteMC(dev, NV_PBUS_POWERCTRL_2, saved_powerctrl_2 & 0xd7ffffff); + if (regoffset == 0x68) { + saved_powerctrl_4 = nvReadMC(dev, NV_PBUS_POWERCTRL_4); + nvWriteMC(dev, NV_PBUS_POWERCTRL_4, saved_powerctrl_4 & 0xffffffcf); + } + + saved_gpio1 = gpio->get(dev, DCB_GPIO_TVDAC1); + saved_gpio0 = gpio->get(dev, DCB_GPIO_TVDAC0); + + gpio->set(dev, DCB_GPIO_TVDAC1, dcb->type == OUTPUT_TV); + gpio->set(dev, DCB_GPIO_TVDAC0, dcb->type == OUTPUT_TV); + + msleep(4); + + saved_routput = NVReadRAMDAC(dev, 0, NV_PRAMDAC_DACCLK + regoffset); + head = (saved_routput & 0x100) >> 8; + + /* if there's a spare crtc, using it will minimise flicker */ + if (!(NVReadVgaCrtc(dev, head, NV_CIO_CRE_RPC1_INDEX) & 0xC0)) + head ^= 1; + + /* nv driver and nv31 use 0xfffffeee, nv34 and 6600 use 0xfffffece */ + routput = (saved_routput & 0xfffffece) | head << 8; + + if (dev_priv->card_type >= NV_40) { + if (dcb->type == OUTPUT_TV) + routput |= 0x1a << 16; + else + routput &= ~(0x1a << 16); + } + + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_DACCLK + regoffset, routput); + msleep(1); + + temp = NVReadRAMDAC(dev, 0, NV_PRAMDAC_DACCLK + regoffset); + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_DACCLK + regoffset, temp | 1); + + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TESTPOINT_DATA, + NV_PRAMDAC_TESTPOINT_DATA_NOTBLANK | testval); + temp = NVReadRAMDAC(dev, head, NV_PRAMDAC_TEST_CONTROL); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TEST_CONTROL, + temp | NV_PRAMDAC_TEST_CONTROL_TP_INS_EN_ASSERTED); + msleep(5); + + sample = NVReadRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL + regoffset); + /* do it again just in case it's a residual current */ + sample &= NVReadRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL + regoffset); + + temp = NVReadRAMDAC(dev, head, NV_PRAMDAC_TEST_CONTROL); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TEST_CONTROL, + temp & ~NV_PRAMDAC_TEST_CONTROL_TP_INS_EN_ASSERTED); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TESTPOINT_DATA, 0); + + /* bios does something more complex for restoring, but I think this is good enough */ + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_DACCLK + regoffset, saved_routput); + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL + regoffset, saved_rtest_ctrl); + if (regoffset == 0x68) + nvWriteMC(dev, NV_PBUS_POWERCTRL_4, saved_powerctrl_4); + nvWriteMC(dev, NV_PBUS_POWERCTRL_2, saved_powerctrl_2); + + gpio->set(dev, DCB_GPIO_TVDAC1, saved_gpio1); + gpio->set(dev, DCB_GPIO_TVDAC0, saved_gpio0); + + return sample; +} + +static enum drm_connector_status +nv17_dac_detect(struct drm_encoder *encoder, struct drm_connector *connector) +{ + struct drm_device *dev = encoder->dev; + struct dcb_entry *dcb = nouveau_encoder(encoder)->dcb; + + if (nv04_dac_in_use(encoder)) + return connector_status_disconnected; + + if (nv17_dac_sample_load(encoder) & + NV_PRAMDAC_TEST_CONTROL_SENSEB_ALLHI) { + NV_INFO(dev, "Load detected on output %c\n", + '@' + ffs(dcb->or)); + return connector_status_connected; + } else { + return connector_status_disconnected; + } +} + +static bool nv04_dac_mode_fixup(struct drm_encoder *encoder, + struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode) +{ + if (nv04_dac_in_use(encoder)) + return false; + + return true; +} + +static void nv04_dac_prepare(struct drm_encoder *encoder) +{ + struct drm_encoder_helper_funcs *helper = encoder->helper_private; + struct drm_device *dev = encoder->dev; + int head = nouveau_crtc(encoder->crtc)->index; + + helper->dpms(encoder, DRM_MODE_DPMS_OFF); + + nv04_dfp_disable(dev, head); +} + +static void nv04_dac_mode_set(struct drm_encoder *encoder, + struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode) +{ + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + int head = nouveau_crtc(encoder->crtc)->index; + + if (nv_gf4_disp_arch(dev)) { + struct drm_encoder *rebind; + uint32_t dac_offset = nv04_dac_output_offset(encoder); + uint32_t otherdac; + + /* bit 16-19 are bits that are set on some G70 cards, + * but don't seem to have much effect */ + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_DACCLK + dac_offset, + head << 8 | NV_PRAMDAC_DACCLK_SEL_DACCLK); + /* force any other vga encoders to bind to the other crtc */ + list_for_each_entry(rebind, &dev->mode_config.encoder_list, head) { + if (rebind == encoder + || nouveau_encoder(rebind)->dcb->type != OUTPUT_ANALOG) + continue; + + dac_offset = nv04_dac_output_offset(rebind); + otherdac = NVReadRAMDAC(dev, 0, NV_PRAMDAC_DACCLK + dac_offset); + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_DACCLK + dac_offset, + (otherdac & ~0x0100) | (head ^ 1) << 8); + } + } + + /* This could use refinement for flatpanels, but it should work this way */ + if (dev_priv->chipset < 0x44) + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL + nv04_dac_output_offset(encoder), 0xf0000000); + else + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL + nv04_dac_output_offset(encoder), 0x00100000); +} + +static void nv04_dac_commit(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct nouveau_crtc *nv_crtc = nouveau_crtc(encoder->crtc); + struct drm_encoder_helper_funcs *helper = encoder->helper_private; + + helper->dpms(encoder, DRM_MODE_DPMS_ON); + + NV_INFO(dev, "Output %s is running on CRTC %d using output %c\n", + drm_get_connector_name(&nouveau_encoder_connector_get(nv_encoder)->base), + nv_crtc->index, '@' + ffs(nv_encoder->dcb->or)); +} + +void nv04_dac_update_dacclk(struct drm_encoder *encoder, bool enable) +{ + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct dcb_entry *dcb = nouveau_encoder(encoder)->dcb; + + if (nv_gf4_disp_arch(dev)) { + uint32_t *dac_users = &dev_priv->dac_users[ffs(dcb->or) - 1]; + int dacclk_off = NV_PRAMDAC_DACCLK + nv04_dac_output_offset(encoder); + uint32_t dacclk = NVReadRAMDAC(dev, 0, dacclk_off); + + if (enable) { + *dac_users |= 1 << dcb->index; + NVWriteRAMDAC(dev, 0, dacclk_off, dacclk | NV_PRAMDAC_DACCLK_SEL_DACCLK); + + } else { + *dac_users &= ~(1 << dcb->index); + if (!*dac_users) + NVWriteRAMDAC(dev, 0, dacclk_off, + dacclk & ~NV_PRAMDAC_DACCLK_SEL_DACCLK); + } + } +} + +/* Check if the DAC corresponding to 'encoder' is being used by + * someone else. */ +bool nv04_dac_in_use(struct drm_encoder *encoder) +{ + struct drm_nouveau_private *dev_priv = encoder->dev->dev_private; + struct dcb_entry *dcb = nouveau_encoder(encoder)->dcb; + + return nv_gf4_disp_arch(encoder->dev) && + (dev_priv->dac_users[ffs(dcb->or) - 1] & ~(1 << dcb->index)); +} + +static void nv04_dac_dpms(struct drm_encoder *encoder, int mode) +{ + struct drm_device *dev = encoder->dev; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + + if (nv_encoder->last_dpms == mode) + return; + nv_encoder->last_dpms = mode; + + NV_INFO(dev, "Setting dpms mode %d on vga encoder (output %d)\n", + mode, nv_encoder->dcb->index); + + nv04_dac_update_dacclk(encoder, mode == DRM_MODE_DPMS_ON); +} + +static void nv04_dac_save(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + + if (nv_gf4_disp_arch(dev)) + nv_encoder->restore.output = NVReadRAMDAC(dev, 0, NV_PRAMDAC_DACCLK + + nv04_dac_output_offset(encoder)); +} + +static void nv04_dac_restore(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + + if (nv_gf4_disp_arch(dev)) + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_DACCLK + nv04_dac_output_offset(encoder), + nv_encoder->restore.output); + + nv_encoder->last_dpms = NV_DPMS_CLEARED; +} + +static void nv04_dac_destroy(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + + NV_DEBUG_KMS(encoder->dev, "\n"); + + drm_encoder_cleanup(encoder); + kfree(nv_encoder); +} + +static const struct drm_encoder_helper_funcs nv04_dac_helper_funcs = { + .dpms = nv04_dac_dpms, + .save = nv04_dac_save, + .restore = nv04_dac_restore, + .mode_fixup = nv04_dac_mode_fixup, + .prepare = nv04_dac_prepare, + .commit = nv04_dac_commit, + .mode_set = nv04_dac_mode_set, + .detect = nv04_dac_detect +}; + +static const struct drm_encoder_helper_funcs nv17_dac_helper_funcs = { + .dpms = nv04_dac_dpms, + .save = nv04_dac_save, + .restore = nv04_dac_restore, + .mode_fixup = nv04_dac_mode_fixup, + .prepare = nv04_dac_prepare, + .commit = nv04_dac_commit, + .mode_set = nv04_dac_mode_set, + .detect = nv17_dac_detect +}; + +static const struct drm_encoder_funcs nv04_dac_funcs = { + .destroy = nv04_dac_destroy, +}; + +int +nv04_dac_create(struct drm_connector *connector, struct dcb_entry *entry) +{ + const struct drm_encoder_helper_funcs *helper; + struct nouveau_encoder *nv_encoder = NULL; + struct drm_device *dev = connector->dev; + struct drm_encoder *encoder; + + nv_encoder = kzalloc(sizeof(*nv_encoder), GFP_KERNEL); + if (!nv_encoder) + return -ENOMEM; + + encoder = to_drm_encoder(nv_encoder); + + nv_encoder->dcb = entry; + nv_encoder->or = ffs(entry->or) - 1; + + if (nv_gf4_disp_arch(dev)) + helper = &nv17_dac_helper_funcs; + else + helper = &nv04_dac_helper_funcs; + + drm_encoder_init(dev, encoder, &nv04_dac_funcs, DRM_MODE_ENCODER_DAC); + drm_encoder_helper_add(encoder, helper); + + encoder->possible_crtcs = entry->heads; + encoder->possible_clones = 0; + + drm_mode_connector_attach_encoder(connector, encoder); + return 0; +} diff --git a/driver/pscnv/nv04_dfp.c b/driver/pscnv/nv04_dfp.c new file mode 100644 index 00000000..ef235504 --- /dev/null +++ b/driver/pscnv/nv04_dfp.c @@ -0,0 +1,717 @@ +/* + * Copyright 2003 NVIDIA, Corporation + * Copyright 2006 Dave Airlie + * Copyright 2007 Maarten Maathuis + * Copyright 2007-2009 Stuart Bennett + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +#include "drmP.h" +#include "drm_crtc_helper.h" + +#include "nouveau_drv.h" +#include "nouveau_encoder.h" +#include "nouveau_connector.h" +#include "nouveau_crtc.h" +#include "nouveau_hw.h" +#include "nvreg.h" + +#include "i2c/sil164.h" + +#define FP_TG_CONTROL_ON (NV_PRAMDAC_FP_TG_CONTROL_DISPEN_POS | \ + NV_PRAMDAC_FP_TG_CONTROL_HSYNC_POS | \ + NV_PRAMDAC_FP_TG_CONTROL_VSYNC_POS) +#define FP_TG_CONTROL_OFF (NV_PRAMDAC_FP_TG_CONTROL_DISPEN_DISABLE | \ + NV_PRAMDAC_FP_TG_CONTROL_HSYNC_DISABLE | \ + NV_PRAMDAC_FP_TG_CONTROL_VSYNC_DISABLE) + +static inline bool is_fpc_off(uint32_t fpc) +{ + return ((fpc & (FP_TG_CONTROL_ON | FP_TG_CONTROL_OFF)) == + FP_TG_CONTROL_OFF); +} + +int nv04_dfp_get_bound_head(struct drm_device *dev, struct dcb_entry *dcbent) +{ + /* special case of nv_read_tmds to find crtc associated with an output. + * this does not give a correct answer for off-chip dvi, but there's no + * use for such an answer anyway + */ + int ramdac = (dcbent->or & OUTPUT_C) >> 2; + + NVWriteRAMDAC(dev, ramdac, NV_PRAMDAC_FP_TMDS_CONTROL, + NV_PRAMDAC_FP_TMDS_CONTROL_WRITE_DISABLE | 0x4); + return ((NVReadRAMDAC(dev, ramdac, NV_PRAMDAC_FP_TMDS_DATA) & 0x8) >> 3) ^ ramdac; +} + +void nv04_dfp_bind_head(struct drm_device *dev, struct dcb_entry *dcbent, + int head, bool dl) +{ + /* The BIOS scripts don't do this for us, sadly + * Luckily we do know the values ;-) + * + * head < 0 indicates we wish to force a setting with the overrideval + * (for VT restore etc.) + */ + + int ramdac = (dcbent->or & OUTPUT_C) >> 2; + uint8_t tmds04 = 0x80; + + if (head != ramdac) + tmds04 = 0x88; + + if (dcbent->type == OUTPUT_LVDS) + tmds04 |= 0x01; + + nv_write_tmds(dev, dcbent->or, 0, 0x04, tmds04); + + if (dl) /* dual link */ + nv_write_tmds(dev, dcbent->or, 1, 0x04, tmds04 ^ 0x08); +} + +void nv04_dfp_disable(struct drm_device *dev, int head) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv04_crtc_reg *crtcstate = dev_priv->mode_reg.crtc_reg; + + if (NVReadRAMDAC(dev, head, NV_PRAMDAC_FP_TG_CONTROL) & + FP_TG_CONTROL_ON) { + /* digital remnants must be cleaned before new crtc + * values programmed. delay is time for the vga stuff + * to realise it's in control again + */ + NVWriteRAMDAC(dev, head, NV_PRAMDAC_FP_TG_CONTROL, + FP_TG_CONTROL_OFF); + msleep(50); + } + /* don't inadvertently turn it on when state written later */ + crtcstate[head].fp_control = FP_TG_CONTROL_OFF; + crtcstate[head].CRTC[NV_CIO_CRE_LCD__INDEX] &= + ~NV_CIO_CRE_LCD_ROUTE_MASK; +} + +void nv04_dfp_update_fp_control(struct drm_encoder *encoder, int mode) +{ + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct drm_crtc *crtc; + struct nouveau_crtc *nv_crtc; + uint32_t *fpc; + + if (mode == DRM_MODE_DPMS_ON) { + nv_crtc = nouveau_crtc(encoder->crtc); + fpc = &dev_priv->mode_reg.crtc_reg[nv_crtc->index].fp_control; + + if (is_fpc_off(*fpc)) { + /* using saved value is ok, as (is_digital && dpms_on && + * fp_control==OFF) is (at present) *only* true when + * fpc's most recent change was by below "off" code + */ + *fpc = nv_crtc->dpms_saved_fp_control; + } + + nv_crtc->fp_users |= 1 << nouveau_encoder(encoder)->dcb->index; + NVWriteRAMDAC(dev, nv_crtc->index, NV_PRAMDAC_FP_TG_CONTROL, *fpc); + } else { + list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { + nv_crtc = nouveau_crtc(crtc); + fpc = &dev_priv->mode_reg.crtc_reg[nv_crtc->index].fp_control; + + nv_crtc->fp_users &= ~(1 << nouveau_encoder(encoder)->dcb->index); + if (!is_fpc_off(*fpc) && !nv_crtc->fp_users) { + nv_crtc->dpms_saved_fp_control = *fpc; + /* cut the FP output */ + *fpc &= ~FP_TG_CONTROL_ON; + *fpc |= FP_TG_CONTROL_OFF; + NVWriteRAMDAC(dev, nv_crtc->index, + NV_PRAMDAC_FP_TG_CONTROL, *fpc); + } + } + } +} + +static struct drm_encoder *get_tmds_slave(struct drm_encoder *encoder) +{ + struct drm_device *dev = encoder->dev; + struct dcb_entry *dcb = nouveau_encoder(encoder)->dcb; + struct drm_encoder *slave; + + if (dcb->type != OUTPUT_TMDS || dcb->location == DCB_LOC_ON_CHIP) + return NULL; + + /* Some BIOSes (e.g. the one in a Quadro FX1000) report several + * TMDS transmitters at the same I2C address, in the same I2C + * bus. This can still work because in that case one of them is + * always hard-wired to a reasonable configuration using straps, + * and the other one needs to be programmed. + * + * I don't think there's a way to know which is which, even the + * blob programs the one exposed via I2C for *both* heads, so + * let's do the same. + */ + list_for_each_entry(slave, &dev->mode_config.encoder_list, head) { + struct dcb_entry *slave_dcb = nouveau_encoder(slave)->dcb; + + if (slave_dcb->type == OUTPUT_TMDS && get_slave_funcs(slave) && + slave_dcb->tmdsconf.slave_addr == dcb->tmdsconf.slave_addr) + return slave; + } + + return NULL; +} + +static bool nv04_dfp_mode_fixup(struct drm_encoder *encoder, + struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct nouveau_connector *nv_connector = nouveau_encoder_connector_get(nv_encoder); + + if (!nv_connector->native_mode || + nv_connector->scaling_mode == DRM_MODE_SCALE_NONE || + mode->hdisplay > nv_connector->native_mode->hdisplay || + mode->vdisplay > nv_connector->native_mode->vdisplay) { + nv_encoder->mode = *adjusted_mode; + + } else { + nv_encoder->mode = *nv_connector->native_mode; + adjusted_mode->clock = nv_connector->native_mode->clock; + } + + return true; +} + +static void nv04_dfp_prepare_sel_clk(struct drm_device *dev, + struct nouveau_encoder *nv_encoder, int head) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv04_mode_state *state = &dev_priv->mode_reg; + uint32_t bits1618 = nv_encoder->dcb->or & OUTPUT_A ? 0x10000 : 0x40000; + + if (nv_encoder->dcb->location != DCB_LOC_ON_CHIP) + return; + + /* SEL_CLK is only used on the primary ramdac + * It toggles spread spectrum PLL output and sets the bindings of PLLs + * to heads on digital outputs + */ + if (head) + state->sel_clk |= bits1618; + else + state->sel_clk &= ~bits1618; + + /* nv30: + * bit 0 NVClk spread spectrum on/off + * bit 2 MemClk spread spectrum on/off + * bit 4 PixClk1 spread spectrum on/off toggle + * bit 6 PixClk2 spread spectrum on/off toggle + * + * nv40 (observations from bios behaviour and mmio traces): + * bits 4&6 as for nv30 + * bits 5&7 head dependent as for bits 4&6, but do not appear with 4&6; + * maybe a different spread mode + * bits 8&10 seen on dual-link dvi outputs, purpose unknown (set by POST scripts) + * The logic behind turning spread spectrum on/off in the first place, + * and which bit-pair to use, is unclear on nv40 (for earlier cards, the fp table + * entry has the necessary info) + */ + if (nv_encoder->dcb->type == OUTPUT_LVDS && dev_priv->saved_reg.sel_clk & 0xf0) { + int shift = (dev_priv->saved_reg.sel_clk & 0x50) ? 0 : 1; + + state->sel_clk &= ~0xf0; + state->sel_clk |= (head ? 0x40 : 0x10) << shift; + } +} + +static void nv04_dfp_prepare(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_encoder_helper_funcs *helper = encoder->helper_private; + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + int head = nouveau_crtc(encoder->crtc)->index; + struct nv04_crtc_reg *crtcstate = dev_priv->mode_reg.crtc_reg; + uint8_t *cr_lcd = &crtcstate[head].CRTC[NV_CIO_CRE_LCD__INDEX]; + uint8_t *cr_lcd_oth = &crtcstate[head ^ 1].CRTC[NV_CIO_CRE_LCD__INDEX]; + + helper->dpms(encoder, DRM_MODE_DPMS_OFF); + + nv04_dfp_prepare_sel_clk(dev, nv_encoder, head); + + *cr_lcd = (*cr_lcd & ~NV_CIO_CRE_LCD_ROUTE_MASK) | 0x3; + + if (nv_two_heads(dev)) { + if (nv_encoder->dcb->location == DCB_LOC_ON_CHIP) + *cr_lcd |= head ? 0x0 : 0x8; + else { + *cr_lcd |= (nv_encoder->dcb->or << 4) & 0x30; + if (nv_encoder->dcb->type == OUTPUT_LVDS) + *cr_lcd |= 0x30; + if ((*cr_lcd & 0x30) == (*cr_lcd_oth & 0x30)) { + /* avoid being connected to both crtcs */ + *cr_lcd_oth &= ~0x30; + NVWriteVgaCrtc(dev, head ^ 1, + NV_CIO_CRE_LCD__INDEX, + *cr_lcd_oth); + } + } + } +} + + +static void nv04_dfp_mode_set(struct drm_encoder *encoder, + struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode) +{ + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_crtc *nv_crtc = nouveau_crtc(encoder->crtc); + struct nv04_crtc_reg *regp = &dev_priv->mode_reg.crtc_reg[nv_crtc->index]; + struct nv04_crtc_reg *savep = &dev_priv->saved_reg.crtc_reg[nv_crtc->index]; + struct nouveau_connector *nv_connector = nouveau_crtc_connector_get(nv_crtc); + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_display_mode *output_mode = &nv_encoder->mode; + uint32_t mode_ratio, panel_ratio; + + NV_DEBUG_KMS(dev, "Output mode on CRTC %d:\n", nv_crtc->index); + drm_mode_debug_printmodeline(output_mode); + + /* Initialize the FP registers in this CRTC. */ + regp->fp_horiz_regs[FP_DISPLAY_END] = output_mode->hdisplay - 1; + regp->fp_horiz_regs[FP_TOTAL] = output_mode->htotal - 1; + if (!nv_gf4_disp_arch(dev) || + (output_mode->hsync_start - output_mode->hdisplay) >= + dev_priv->vbios.digital_min_front_porch) + regp->fp_horiz_regs[FP_CRTC] = output_mode->hdisplay; + else + regp->fp_horiz_regs[FP_CRTC] = output_mode->hsync_start - dev_priv->vbios.digital_min_front_porch - 1; + regp->fp_horiz_regs[FP_SYNC_START] = output_mode->hsync_start - 1; + regp->fp_horiz_regs[FP_SYNC_END] = output_mode->hsync_end - 1; + regp->fp_horiz_regs[FP_VALID_START] = output_mode->hskew; + regp->fp_horiz_regs[FP_VALID_END] = output_mode->hdisplay - 1; + + regp->fp_vert_regs[FP_DISPLAY_END] = output_mode->vdisplay - 1; + regp->fp_vert_regs[FP_TOTAL] = output_mode->vtotal - 1; + regp->fp_vert_regs[FP_CRTC] = output_mode->vtotal - 5 - 1; + regp->fp_vert_regs[FP_SYNC_START] = output_mode->vsync_start - 1; + regp->fp_vert_regs[FP_SYNC_END] = output_mode->vsync_end - 1; + regp->fp_vert_regs[FP_VALID_START] = 0; + regp->fp_vert_regs[FP_VALID_END] = output_mode->vdisplay - 1; + + /* bit26: a bit seen on some g7x, no as yet discernable purpose */ + regp->fp_control = NV_PRAMDAC_FP_TG_CONTROL_DISPEN_POS | + (savep->fp_control & (1 << 26 | NV_PRAMDAC_FP_TG_CONTROL_READ_PROG)); + /* Deal with vsync/hsync polarity */ + /* LVDS screens do set this, but modes with +ve syncs are very rare */ + if (output_mode->flags & DRM_MODE_FLAG_PVSYNC) + regp->fp_control |= NV_PRAMDAC_FP_TG_CONTROL_VSYNC_POS; + if (output_mode->flags & DRM_MODE_FLAG_PHSYNC) + regp->fp_control |= NV_PRAMDAC_FP_TG_CONTROL_HSYNC_POS; + /* panel scaling first, as native would get set otherwise */ + if (nv_connector->scaling_mode == DRM_MODE_SCALE_NONE || + nv_connector->scaling_mode == DRM_MODE_SCALE_CENTER) /* panel handles it */ + regp->fp_control |= NV_PRAMDAC_FP_TG_CONTROL_MODE_CENTER; + else if (adjusted_mode->hdisplay == output_mode->hdisplay && + adjusted_mode->vdisplay == output_mode->vdisplay) /* native mode */ + regp->fp_control |= NV_PRAMDAC_FP_TG_CONTROL_MODE_NATIVE; + else /* gpu needs to scale */ + regp->fp_control |= NV_PRAMDAC_FP_TG_CONTROL_MODE_SCALE; + if (nvReadEXTDEV(dev, NV_PEXTDEV_BOOT_0) & NV_PEXTDEV_BOOT_0_STRAP_FP_IFACE_12BIT) + regp->fp_control |= NV_PRAMDAC_FP_TG_CONTROL_WIDTH_12; + if (nv_encoder->dcb->location != DCB_LOC_ON_CHIP && + output_mode->clock > 165000) + regp->fp_control |= (2 << 24); + if (nv_encoder->dcb->type == OUTPUT_LVDS) { + bool duallink, dummy; + + nouveau_bios_parse_lvds_table(dev, nv_connector->native_mode-> + clock, &duallink, &dummy); + if (duallink) + regp->fp_control |= (8 << 28); + } else + if (output_mode->clock > 165000) + regp->fp_control |= (8 << 28); + + regp->fp_debug_0 = NV_PRAMDAC_FP_DEBUG_0_YWEIGHT_ROUND | + NV_PRAMDAC_FP_DEBUG_0_XWEIGHT_ROUND | + NV_PRAMDAC_FP_DEBUG_0_YINTERP_BILINEAR | + NV_PRAMDAC_FP_DEBUG_0_XINTERP_BILINEAR | + NV_RAMDAC_FP_DEBUG_0_TMDS_ENABLED | + NV_PRAMDAC_FP_DEBUG_0_YSCALE_ENABLE | + NV_PRAMDAC_FP_DEBUG_0_XSCALE_ENABLE; + + /* We want automatic scaling */ + regp->fp_debug_1 = 0; + /* This can override HTOTAL and VTOTAL */ + regp->fp_debug_2 = 0; + + /* Use 20.12 fixed point format to avoid floats */ + mode_ratio = (1 << 12) * adjusted_mode->hdisplay / adjusted_mode->vdisplay; + panel_ratio = (1 << 12) * output_mode->hdisplay / output_mode->vdisplay; + /* if ratios are equal, SCALE_ASPECT will automatically (and correctly) + * get treated the same as SCALE_FULLSCREEN */ + if (nv_connector->scaling_mode == DRM_MODE_SCALE_ASPECT && + mode_ratio != panel_ratio) { + uint32_t diff, scale; + bool divide_by_2 = nv_gf4_disp_arch(dev); + + if (mode_ratio < panel_ratio) { + /* vertical needs to expand to glass size (automatic) + * horizontal needs to be scaled at vertical scale factor + * to maintain aspect */ + + scale = (1 << 12) * adjusted_mode->vdisplay / output_mode->vdisplay; + regp->fp_debug_1 = NV_PRAMDAC_FP_DEBUG_1_XSCALE_TESTMODE_ENABLE | + XLATE(scale, divide_by_2, NV_PRAMDAC_FP_DEBUG_1_XSCALE_VALUE); + + /* restrict area of screen used, horizontally */ + diff = output_mode->hdisplay - + output_mode->vdisplay * mode_ratio / (1 << 12); + regp->fp_horiz_regs[FP_VALID_START] += diff / 2; + regp->fp_horiz_regs[FP_VALID_END] -= diff / 2; + } + + if (mode_ratio > panel_ratio) { + /* horizontal needs to expand to glass size (automatic) + * vertical needs to be scaled at horizontal scale factor + * to maintain aspect */ + + scale = (1 << 12) * adjusted_mode->hdisplay / output_mode->hdisplay; + regp->fp_debug_1 = NV_PRAMDAC_FP_DEBUG_1_YSCALE_TESTMODE_ENABLE | + XLATE(scale, divide_by_2, NV_PRAMDAC_FP_DEBUG_1_YSCALE_VALUE); + + /* restrict area of screen used, vertically */ + diff = output_mode->vdisplay - + (1 << 12) * output_mode->hdisplay / mode_ratio; + regp->fp_vert_regs[FP_VALID_START] += diff / 2; + regp->fp_vert_regs[FP_VALID_END] -= diff / 2; + } + } + + /* Output property. */ + if (nv_connector->use_dithering) { + if (dev_priv->chipset == 0x11) + regp->dither = savep->dither | 0x00010000; + else { + int i; + regp->dither = savep->dither | 0x00000001; + for (i = 0; i < 3; i++) { + regp->dither_regs[i] = 0xe4e4e4e4; + regp->dither_regs[i + 3] = 0x44444444; + } + } + } else { + if (dev_priv->chipset != 0x11) { + /* reset them */ + int i; + for (i = 0; i < 3; i++) { + regp->dither_regs[i] = savep->dither_regs[i]; + regp->dither_regs[i + 3] = savep->dither_regs[i + 3]; + } + } + regp->dither = savep->dither; + } + + regp->fp_margin_color = 0; +} + +static void nv04_dfp_commit(struct drm_encoder *encoder) +{ + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct drm_encoder_helper_funcs *helper = encoder->helper_private; + struct nouveau_crtc *nv_crtc = nouveau_crtc(encoder->crtc); + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct dcb_entry *dcbe = nv_encoder->dcb; + int head = nouveau_crtc(encoder->crtc)->index; + struct drm_encoder *slave_encoder; + + if (dcbe->type == OUTPUT_TMDS) + run_tmds_table(dev, dcbe, head, nv_encoder->mode.clock); + else if (dcbe->type == OUTPUT_LVDS) + call_lvds_script(dev, dcbe, head, LVDS_RESET, nv_encoder->mode.clock); + + /* update fp_control state for any changes made by scripts, + * so correct value is written at DPMS on */ + dev_priv->mode_reg.crtc_reg[head].fp_control = + NVReadRAMDAC(dev, head, NV_PRAMDAC_FP_TG_CONTROL); + + /* This could use refinement for flatpanels, but it should work this way */ + if (dev_priv->chipset < 0x44) + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL + nv04_dac_output_offset(encoder), 0xf0000000); + else + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_TEST_CONTROL + nv04_dac_output_offset(encoder), 0x00100000); + + /* Init external transmitters */ + slave_encoder = get_tmds_slave(encoder); + if (slave_encoder) + get_slave_funcs(slave_encoder)->mode_set( + slave_encoder, &nv_encoder->mode, &nv_encoder->mode); + + helper->dpms(encoder, DRM_MODE_DPMS_ON); + + NV_INFO(dev, "Output %s is running on CRTC %d using output %c\n", + drm_get_connector_name(&nouveau_encoder_connector_get(nv_encoder)->base), + nv_crtc->index, '@' + ffs(nv_encoder->dcb->or)); +} + +static void nv04_dfp_update_backlight(struct drm_encoder *encoder, int mode) +{ +#ifdef __powerpc__ + struct drm_device *dev = encoder->dev; + + /* BIOS scripts usually take care of the backlight, thanks + * Apple for your consistency. + */ + if (dev->pci_device == 0x0179 || dev->pci_device == 0x0189 || + dev->pci_device == 0x0329) { + if (mode == DRM_MODE_DPMS_ON) { + nv_mask(dev, NV_PBUS_DEBUG_DUALHEAD_CTL, 0, 1 << 31); + nv_mask(dev, NV_PCRTC_GPIO_EXT, 3, 1); + } else { + nv_mask(dev, NV_PBUS_DEBUG_DUALHEAD_CTL, 1 << 31, 0); + nv_mask(dev, NV_PCRTC_GPIO_EXT, 3, 0); + } + } +#endif +} + +static inline bool is_powersaving_dpms(int mode) +{ + return (mode != DRM_MODE_DPMS_ON); +} + +static void nv04_lvds_dpms(struct drm_encoder *encoder, int mode) +{ + struct drm_device *dev = encoder->dev; + struct drm_crtc *crtc = encoder->crtc; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + bool was_powersaving = is_powersaving_dpms(nv_encoder->last_dpms); + + if (nv_encoder->last_dpms == mode) + return; + nv_encoder->last_dpms = mode; + + NV_INFO(dev, "Setting dpms mode %d on lvds encoder (output %d)\n", + mode, nv_encoder->dcb->index); + + if (was_powersaving && is_powersaving_dpms(mode)) + return; + + if (nv_encoder->dcb->lvdsconf.use_power_scripts) { + struct nouveau_connector *nv_connector = nouveau_encoder_connector_get(nv_encoder); + + /* when removing an output, crtc may not be set, but PANEL_OFF + * must still be run + */ + int head = crtc ? nouveau_crtc(crtc)->index : + nv04_dfp_get_bound_head(dev, nv_encoder->dcb); + + if (mode == DRM_MODE_DPMS_ON) { + if (!nv_connector->native_mode) { + NV_ERROR(dev, "Not turning on LVDS without native mode\n"); + return; + } + call_lvds_script(dev, nv_encoder->dcb, head, + LVDS_PANEL_ON, nv_connector->native_mode->clock); + } else + /* pxclk of 0 is fine for PANEL_OFF, and for a + * disconnected LVDS encoder there is no native_mode + */ + call_lvds_script(dev, nv_encoder->dcb, head, + LVDS_PANEL_OFF, 0); + } + + nv04_dfp_update_backlight(encoder, mode); + nv04_dfp_update_fp_control(encoder, mode); + + if (mode == DRM_MODE_DPMS_ON) + nv04_dfp_prepare_sel_clk(dev, nv_encoder, nouveau_crtc(crtc)->index); + else { + dev_priv->mode_reg.sel_clk = NVReadRAMDAC(dev, 0, NV_PRAMDAC_SEL_CLK); + dev_priv->mode_reg.sel_clk &= ~0xf0; + } + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_SEL_CLK, dev_priv->mode_reg.sel_clk); +} + +static void nv04_tmds_dpms(struct drm_encoder *encoder, int mode) +{ + struct drm_device *dev = encoder->dev; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + + if (nv_encoder->last_dpms == mode) + return; + nv_encoder->last_dpms = mode; + + NV_INFO(dev, "Setting dpms mode %d on tmds encoder (output %d)\n", + mode, nv_encoder->dcb->index); + + nv04_dfp_update_backlight(encoder, mode); + nv04_dfp_update_fp_control(encoder, mode); +} + +static void nv04_dfp_save(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + + if (nv_two_heads(dev)) + nv_encoder->restore.head = + nv04_dfp_get_bound_head(dev, nv_encoder->dcb); +} + +static void nv04_dfp_restore(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + int head = nv_encoder->restore.head; + + if (nv_encoder->dcb->type == OUTPUT_LVDS) { + struct drm_display_mode *native_mode = nouveau_encoder_connector_get(nv_encoder)->native_mode; + if (native_mode) + call_lvds_script(dev, nv_encoder->dcb, head, LVDS_PANEL_ON, + native_mode->clock); + else + NV_ERROR(dev, "Not restoring LVDS without native mode\n"); + + } else if (nv_encoder->dcb->type == OUTPUT_TMDS) { + int clock = nouveau_hw_pllvals_to_clk + (&dev_priv->saved_reg.crtc_reg[head].pllvals); + + run_tmds_table(dev, nv_encoder->dcb, head, clock); + } + + nv_encoder->last_dpms = NV_DPMS_CLEARED; +} + +static void nv04_dfp_destroy(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + + NV_DEBUG_KMS(encoder->dev, "\n"); + + if (get_slave_funcs(encoder)) + get_slave_funcs(encoder)->destroy(encoder); + + drm_encoder_cleanup(encoder); + kfree(nv_encoder); +} + +static void nv04_tmds_slave_init(struct drm_encoder *encoder) +{ + struct drm_device *dev = encoder->dev; + struct dcb_entry *dcb = nouveau_encoder(encoder)->dcb; + struct nouveau_i2c_chan *i2c = nouveau_i2c_find(dev, 2); + struct i2c_board_info info[] = { + { + .type = "sil164", + .addr = (dcb->tmdsconf.slave_addr == 0x7 ? 0x3a : 0x38), + .platform_data = &(struct sil164_encoder_params) { + SIL164_INPUT_EDGE_RISING + } + }, + { } + }; + int type; + + if (!nv_gf4_disp_arch(dev) || !i2c || + get_tmds_slave(encoder)) + return; + + type = nouveau_i2c_identify(dev, "TMDS transmitter", info, NULL, 2); + if (type < 0) + return; + + drm_i2c_encoder_init(dev, to_encoder_slave(encoder), + &i2c->adapter, &info[type]); +} + +static const struct drm_encoder_helper_funcs nv04_lvds_helper_funcs = { + .dpms = nv04_lvds_dpms, + .save = nv04_dfp_save, + .restore = nv04_dfp_restore, + .mode_fixup = nv04_dfp_mode_fixup, + .prepare = nv04_dfp_prepare, + .commit = nv04_dfp_commit, + .mode_set = nv04_dfp_mode_set, + .detect = NULL, +}; + +static const struct drm_encoder_helper_funcs nv04_tmds_helper_funcs = { + .dpms = nv04_tmds_dpms, + .save = nv04_dfp_save, + .restore = nv04_dfp_restore, + .mode_fixup = nv04_dfp_mode_fixup, + .prepare = nv04_dfp_prepare, + .commit = nv04_dfp_commit, + .mode_set = nv04_dfp_mode_set, + .detect = NULL, +}; + +static const struct drm_encoder_funcs nv04_dfp_funcs = { + .destroy = nv04_dfp_destroy, +}; + +int +nv04_dfp_create(struct drm_connector *connector, struct dcb_entry *entry) +{ + const struct drm_encoder_helper_funcs *helper; + struct nouveau_encoder *nv_encoder = NULL; + struct drm_encoder *encoder; + int type; + + switch (entry->type) { + case OUTPUT_TMDS: + type = DRM_MODE_ENCODER_TMDS; + helper = &nv04_tmds_helper_funcs; + break; + case OUTPUT_LVDS: + type = DRM_MODE_ENCODER_LVDS; + helper = &nv04_lvds_helper_funcs; + break; + default: + return -EINVAL; + } + + nv_encoder = kzalloc(sizeof(*nv_encoder), GFP_KERNEL); + if (!nv_encoder) + return -ENOMEM; + + encoder = to_drm_encoder(nv_encoder); + + nv_encoder->dcb = entry; + nv_encoder->or = ffs(entry->or) - 1; + + drm_encoder_init(connector->dev, encoder, &nv04_dfp_funcs, type); + drm_encoder_helper_add(encoder, helper); + + encoder->possible_crtcs = entry->heads; + encoder->possible_clones = 0; + + if (entry->type == OUTPUT_TMDS && + entry->location != DCB_LOC_ON_CHIP) + nv04_tmds_slave_init(encoder); + + drm_mode_connector_attach_encoder(connector, encoder); + return 0; +} diff --git a/driver/pscnv/nv04_pm.c b/driver/pscnv/nv04_pm.c new file mode 100644 index 00000000..6a6eb697 --- /dev/null +++ b/driver/pscnv/nv04_pm.c @@ -0,0 +1,81 @@ +/* + * Copyright 2010 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_hw.h" +#include "nouveau_pm.h" + +struct nv04_pm_state { + struct pll_lims pll; + struct nouveau_pll_vals calc; +}; + +int +nv04_pm_clock_get(struct drm_device *dev, u32 id) +{ + return nouveau_hw_get_clock(dev, id); +} + +void * +nv04_pm_clock_pre(struct drm_device *dev, struct nouveau_pm_level *perflvl, + u32 id, int khz) +{ + struct nv04_pm_state *state; + int ret; + + state = kzalloc(sizeof(*state), GFP_KERNEL); + if (!state) + return ERR_PTR(-ENOMEM); + + ret = get_pll_limits(dev, id, &state->pll); + if (ret) { + kfree(state); + return (ret == -ENOENT) ? NULL : ERR_PTR(ret); + } + + ret = nouveau_calc_pll_mnp(dev, &state->pll, khz, &state->calc); + if (!ret) { + kfree(state); + return ERR_PTR(-EINVAL); + } + + return state; +} + +void +nv04_pm_clock_set(struct drm_device *dev, void *pre_state) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv04_pm_state *state = pre_state; + u32 reg = state->pll.reg; + + /* thank the insane nouveau_hw_setpll() interface for this */ + if (dev_priv->card_type >= NV_40) + reg += 4; + + nouveau_hw_setpll(dev, reg, &state->calc); + kfree(state); +} + diff --git a/driver/pscnv/nv04_timer.c b/driver/pscnv/nv04_timer.c new file mode 100644 index 00000000..2d4f57b8 --- /dev/null +++ b/driver/pscnv/nv04_timer.c @@ -0,0 +1,46 @@ +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "nouveau_reg.h" + +int +nv04_timer_init(struct drm_device *dev) +{ + nv_wr32(dev, NV04_PTIMER_INTR_EN_0, 0x00000000); + nv_wr32(dev, NV04_PTIMER_INTR_0, 0xFFFFFFFF); + + /* Just use the pre-existing values when possible for now; these regs + * are not written in nv (driver writer missed a /4 on the address), and + * writing 8 and 3 to the correct regs breaks the timings on the LVDS + * hardware sequencing microcode. + * A correct solution (involving calculations with the GPU PLL) can + * be done when kernel modesetting lands + */ + if (!nv_rd32(dev, NV04_PTIMER_NUMERATOR) || + !nv_rd32(dev, NV04_PTIMER_DENOMINATOR)) { + nv_wr32(dev, NV04_PTIMER_NUMERATOR, 0x00000008); + nv_wr32(dev, NV04_PTIMER_DENOMINATOR, 0x00000003); + } + + return 0; +} + +uint64_t +nv04_timer_read(struct drm_device *dev) +{ + uint32_t low; + /* From kmmio dumps on nv28 this looks like how the blob does this. + * It reads the high dword twice, before and after. + * The only explanation seems to be that the 64-bit timer counter + * advances between high and low dword reads and may corrupt the + * result. Not confirmed. + */ + uint32_t high2 = nv_rd32(dev, NV04_PTIMER_TIME_1); + uint32_t high1; + do { + high1 = high2; + low = nv_rd32(dev, NV04_PTIMER_TIME_0); + high2 = nv_rd32(dev, NV04_PTIMER_TIME_1); + } while (high1 != high2); + return (((uint64_t)high2) << 32) | (uint64_t)low; +} diff --git a/driver/pscnv/nv04_tv.c b/driver/pscnv/nv04_tv.c new file mode 100644 index 00000000..3eb605dd --- /dev/null +++ b/driver/pscnv/nv04_tv.c @@ -0,0 +1,254 @@ +/* + * Copyright (C) 2009 Francisco Jerez. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_encoder.h" +#include "nouveau_connector.h" +#include "nouveau_crtc.h" +#include "nouveau_hw.h" +#include "drm_crtc_helper.h" + +#include "i2c/ch7006.h" + +static struct i2c_board_info nv04_tv_encoder_info[] = { + { + I2C_BOARD_INFO("ch7006", 0x75), + .platform_data = &(struct ch7006_encoder_params) { + CH7006_FORMAT_RGB24m12I, CH7006_CLOCK_MASTER, + 0, 0, 0, + CH7006_SYNC_SLAVE, CH7006_SYNC_SEPARATED, + CH7006_POUT_3_3V, CH7006_ACTIVE_HSYNC + } + }, + { } +}; + +int nv04_tv_identify(struct drm_device *dev, int i2c_index) +{ + return nouveau_i2c_identify(dev, "TV encoder", nv04_tv_encoder_info, + NULL, i2c_index); +} + + +#define PLLSEL_TV_CRTC1_MASK \ + (NV_PRAMDAC_PLL_COEFF_SELECT_TV_VSCLK1 \ + | NV_PRAMDAC_PLL_COEFF_SELECT_TV_PCLK1) +#define PLLSEL_TV_CRTC2_MASK \ + (NV_PRAMDAC_PLL_COEFF_SELECT_TV_VSCLK2 \ + | NV_PRAMDAC_PLL_COEFF_SELECT_TV_PCLK2) + +static void nv04_tv_dpms(struct drm_encoder *encoder, int mode) +{ + struct drm_device *dev = encoder->dev; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv04_mode_state *state = &dev_priv->mode_reg; + uint8_t crtc1A; + + NV_INFO(dev, "Setting dpms mode %d on TV encoder (output %d)\n", + mode, nv_encoder->dcb->index); + + state->pllsel &= ~(PLLSEL_TV_CRTC1_MASK | PLLSEL_TV_CRTC2_MASK); + + if (mode == DRM_MODE_DPMS_ON) { + int head = nouveau_crtc(encoder->crtc)->index; + crtc1A = NVReadVgaCrtc(dev, head, NV_CIO_CRE_RPC1_INDEX); + + state->pllsel |= head ? PLLSEL_TV_CRTC2_MASK : + PLLSEL_TV_CRTC1_MASK; + + /* Inhibit hsync */ + crtc1A |= 0x80; + + NVWriteVgaCrtc(dev, head, NV_CIO_CRE_RPC1_INDEX, crtc1A); + } + + NVWriteRAMDAC(dev, 0, NV_PRAMDAC_PLL_COEFF_SELECT, state->pllsel); + + get_slave_funcs(encoder)->dpms(encoder, mode); +} + +static void nv04_tv_bind(struct drm_device *dev, int head, bool bind) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv04_crtc_reg *state = &dev_priv->mode_reg.crtc_reg[head]; + + state->tv_setup = 0; + + if (bind) + state->CRTC[NV_CIO_CRE_49] |= 0x10; + else + state->CRTC[NV_CIO_CRE_49] &= ~0x10; + + NVWriteVgaCrtc(dev, head, NV_CIO_CRE_LCD__INDEX, + state->CRTC[NV_CIO_CRE_LCD__INDEX]); + NVWriteVgaCrtc(dev, head, NV_CIO_CRE_49, + state->CRTC[NV_CIO_CRE_49]); + NVWriteRAMDAC(dev, head, NV_PRAMDAC_TV_SETUP, + state->tv_setup); +} + +static void nv04_tv_prepare(struct drm_encoder *encoder) +{ + struct drm_device *dev = encoder->dev; + int head = nouveau_crtc(encoder->crtc)->index; + struct drm_encoder_helper_funcs *helper = encoder->helper_private; + + helper->dpms(encoder, DRM_MODE_DPMS_OFF); + + nv04_dfp_disable(dev, head); + + if (nv_two_heads(dev)) + nv04_tv_bind(dev, head ^ 1, false); + + nv04_tv_bind(dev, head, true); +} + +static void nv04_tv_mode_set(struct drm_encoder *encoder, + struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode) +{ + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_crtc *nv_crtc = nouveau_crtc(encoder->crtc); + struct nv04_crtc_reg *regp = &dev_priv->mode_reg.crtc_reg[nv_crtc->index]; + + regp->tv_htotal = adjusted_mode->htotal; + regp->tv_vtotal = adjusted_mode->vtotal; + + /* These delay the TV signals with respect to the VGA port, + * they might be useful if we ever allow a CRTC to drive + * multiple outputs. + */ + regp->tv_hskew = 1; + regp->tv_hsync_delay = 1; + regp->tv_hsync_delay2 = 64; + regp->tv_vskew = 1; + regp->tv_vsync_delay = 1; + + get_slave_funcs(encoder)->mode_set(encoder, mode, adjusted_mode); +} + +static void nv04_tv_commit(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct nouveau_crtc *nv_crtc = nouveau_crtc(encoder->crtc); + struct drm_encoder_helper_funcs *helper = encoder->helper_private; + + helper->dpms(encoder, DRM_MODE_DPMS_ON); + + NV_INFO(dev, "Output %s is running on CRTC %d using output %c\n", + drm_get_connector_name(&nouveau_encoder_connector_get(nv_encoder)->base), nv_crtc->index, + '@' + ffs(nv_encoder->dcb->or)); +} + +static void nv04_tv_destroy(struct drm_encoder *encoder) +{ + get_slave_funcs(encoder)->destroy(encoder); + drm_encoder_cleanup(encoder); + + kfree(encoder->helper_private); + kfree(nouveau_encoder(encoder)); +} + +static const struct drm_encoder_funcs nv04_tv_funcs = { + .destroy = nv04_tv_destroy, +}; + +int +nv04_tv_create(struct drm_connector *connector, struct dcb_entry *entry) +{ + struct nouveau_encoder *nv_encoder; + struct drm_encoder *encoder; + struct drm_device *dev = connector->dev; + struct drm_encoder_helper_funcs *hfuncs; + struct drm_encoder_slave_funcs *sfuncs; + struct nouveau_i2c_chan *i2c = + nouveau_i2c_find(dev, entry->i2c_index); + int type, ret; + + /* Ensure that we can talk to this encoder */ + type = nv04_tv_identify(dev, entry->i2c_index); + if (type < 0) + return type; + + /* Allocate the necessary memory */ + nv_encoder = kzalloc(sizeof(*nv_encoder), GFP_KERNEL); + if (!nv_encoder) + return -ENOMEM; + + hfuncs = kzalloc(sizeof(*hfuncs), GFP_KERNEL); + if (!hfuncs) { + ret = -ENOMEM; + goto fail_free; + } + + /* Initialize the common members */ + encoder = to_drm_encoder(nv_encoder); + + drm_encoder_init(dev, encoder, &nv04_tv_funcs, DRM_MODE_ENCODER_TVDAC); + drm_encoder_helper_add(encoder, hfuncs); + + encoder->possible_crtcs = entry->heads; + encoder->possible_clones = 0; + nv_encoder->dcb = entry; + nv_encoder->or = ffs(entry->or) - 1; + + /* Run the slave-specific initialization */ + ret = drm_i2c_encoder_init(dev, to_encoder_slave(encoder), + &i2c->adapter, &nv04_tv_encoder_info[type]); + if (ret < 0) + goto fail_cleanup; + + /* Fill the function pointers */ + sfuncs = get_slave_funcs(encoder); + + *hfuncs = (struct drm_encoder_helper_funcs) { + .dpms = nv04_tv_dpms, + .save = sfuncs->save, + .restore = sfuncs->restore, + .mode_fixup = sfuncs->mode_fixup, + .prepare = nv04_tv_prepare, + .commit = nv04_tv_commit, + .mode_set = nv04_tv_mode_set, + .detect = sfuncs->detect, + }; + + /* Attach it to the specified connector. */ + sfuncs->create_resources(encoder, connector); + drm_mode_connector_attach_encoder(connector, encoder); + + return 0; + +fail_cleanup: + drm_encoder_cleanup(encoder); + kfree(hfuncs); +fail_free: + kfree(nv_encoder); + return ret; +} diff --git a/driver/pscnv/nv10_gpio.c b/driver/pscnv/nv10_gpio.c new file mode 100644 index 00000000..007fc29e --- /dev/null +++ b/driver/pscnv/nv10_gpio.c @@ -0,0 +1,92 @@ +/* + * Copyright (C) 2009 Francisco Jerez. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_hw.h" + +static bool +get_gpio_location(struct dcb_gpio_entry *ent, uint32_t *reg, uint32_t *shift, + uint32_t *mask) +{ + if (ent->line < 2) { + *reg = NV_PCRTC_GPIO; + *shift = ent->line * 16; + *mask = 0x11; + + } else if (ent->line < 10) { + *reg = NV_PCRTC_GPIO_EXT; + *shift = (ent->line - 2) * 4; + *mask = 0x3; + + } else if (ent->line < 14) { + *reg = NV_PCRTC_850; + *shift = (ent->line - 10) * 4; + *mask = 0x3; + + } else { + return false; + } + + return true; +} + +int +nv10_gpio_get(struct drm_device *dev, enum dcb_gpio_tag tag) +{ + struct dcb_gpio_entry *ent = nouveau_bios_gpio_entry(dev, tag); + uint32_t reg, shift, mask, value; + + if (!ent) + return -ENODEV; + + if (!get_gpio_location(ent, ®, &shift, &mask)) + return -ENODEV; + + value = NVReadCRTC(dev, 0, reg) >> shift; + + return (ent->invert ? 1 : 0) ^ (value & 1); +} + +int +nv10_gpio_set(struct drm_device *dev, enum dcb_gpio_tag tag, int state) +{ + struct dcb_gpio_entry *ent = nouveau_bios_gpio_entry(dev, tag); + uint32_t reg, shift, mask, value; + + if (!ent) + return -ENODEV; + + if (!get_gpio_location(ent, ®, &shift, &mask)) + return -ENODEV; + + value = ((ent->invert ? 1 : 0) ^ (state ? 1 : 0)) << shift; + mask = ~(mask << shift); + + NVWriteCRTC(dev, 0, reg, value | (NVReadCRTC(dev, 0, reg) & mask)); + + return 0; +} diff --git a/driver/pscnv/nv50_calc.c b/driver/pscnv/nv50_calc.c new file mode 100644 index 00000000..2cdc2bfe --- /dev/null +++ b/driver/pscnv/nv50_calc.c @@ -0,0 +1,87 @@ +/* + * Copyright 2010 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" +#include "drm_fixed.h" +#include "nouveau_drv.h" +#include "nouveau_hw.h" + +int +nv50_calc_pll(struct drm_device *dev, struct pll_lims *pll, int clk, + int *N1, int *M1, int *N2, int *M2, int *P) +{ + struct nouveau_pll_vals pll_vals; + int ret; + + ret = nouveau_calc_pll_mnp(dev, pll, clk, &pll_vals); + if (ret <= 0) + return ret; + + *N1 = pll_vals.N1; + *M1 = pll_vals.M1; + *N2 = pll_vals.N2; + *M2 = pll_vals.M2; + *P = pll_vals.log2P; + return ret; +} + +int +nv50_calc_pll2(struct drm_device *dev, struct pll_lims *pll, int clk, + int *N, int *fN, int *M, int *P) +{ + fixed20_12 fb_div, a, b; + + *P = pll->vco1.maxfreq / clk; + if (*P > pll->max_p) + *P = pll->max_p; + if (*P < pll->min_p) + *P = pll->min_p; + + /* *M = ceil(refclk / pll->vco.max_inputfreq); */ + a.full = dfixed_const(pll->refclk); + b.full = dfixed_const(pll->vco1.max_inputfreq); + a.full = dfixed_div(a, b); + a.full = dfixed_ceil(a); + *M = dfixed_trunc(a); + + /* fb_div = (vco * *M) / refclk; */ + fb_div.full = dfixed_const(clk * *P); + fb_div.full = dfixed_mul(fb_div, a); + a.full = dfixed_const(pll->refclk); + fb_div.full = dfixed_div(fb_div, a); + + /* *N = floor(fb_div); */ + a.full = dfixed_floor(fb_div); + *N = dfixed_trunc(fb_div); + + /* *fN = (fmod(fb_div, 1.0) * 8192) - 4096; */ + b.full = dfixed_const(8192); + a.full = dfixed_mul(a, b); + fb_div.full = dfixed_mul(fb_div, b); + fb_div.full = fb_div.full - a.full; + *fN = dfixed_trunc(fb_div) - 4096; + *fN &= 0xffff; + + return clk; +} diff --git a/driver/pscnv/nv50_chan.c b/driver/pscnv/nv50_chan.c new file mode 100644 index 00000000..b47f906e --- /dev/null +++ b/driver/pscnv/nv50_chan.c @@ -0,0 +1,180 @@ +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "nv50_chan.h" +#include "pscnv_chan.h" +#include "nv50_vm.h" + +int nv50_chan_new (struct pscnv_chan *ch) { + struct pscnv_vspace *vs = ch->vspace; + struct drm_nouveau_private *dev_priv = ch->dev->dev_private; + uint64_t size; + uint32_t chan_pd; + unsigned long flags; + int i; + /* determine size of underlying VO... for normal channels, + * allocate 64kiB since they have to store the objects + * heap. for the BAR fake channel, we'll only need two objects, + * so keep it minimal + */ + if (ch->cid >= 0) + size = 0x10000; + else if (dev_priv->chipset == 0x50) + size = 0x6000; + else + size = 0x5000; + ch->bo = pscnv_mem_alloc(vs->dev, size, PSCNV_GEM_CONTIG, + 0, (ch->cid == -1 ? 0xc5a2ba7 : 0xc5a2f1f0)); + if (!ch->bo) + return -ENOMEM; + + spin_lock_irqsave(&dev_priv->chan->ch_lock, flags); + ch->handle = ch->bo->start >> 12; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + + if (vs->vid != -1) + dev_priv->vm->map_kernel(ch->bo); + + mutex_lock(&vs->lock); + list_add(&ch->vspace_list, &nv50_vs(vs)->chan_list); + if (dev_priv->chipset == 0x50) + chan_pd = NV50_CHAN_PD; + else + chan_pd = NV84_CHAN_PD; + for (i = 0; i < NV50_VM_PDE_COUNT; i++) { + if (nv50_vs(vs)->pt[i]) { + nv_wv32(ch->bo, chan_pd + i * 8 + 4, nv50_vs(vs)->pt[i]->start >> 32); + nv_wv32(ch->bo, chan_pd + i * 8, nv50_vs(vs)->pt[i]->start | 0x3); + } else { + nv_wv32(ch->bo, chan_pd + i * 8, 0); + } + } + mutex_unlock(&vs->lock); + + ch->instpos = chan_pd + NV50_VM_PDE_COUNT * 8; + + if (ch->cid >= 0) { + int i; + ch->ramht.bo = ch->bo; + ch->ramht.bits = 9; + ch->ramht.offset = nv50_chan_iobj_new(ch, 8 << ch->ramht.bits); + for (i = 0; i < (8 << ch->ramht.bits); i += 8) + nv_wv32(ch->ramht.bo, ch->ramht.offset + i + 4, 0); + + if (dev_priv->chipset == 0x50) { + ch->ramfc = 0; + } else { + /* actually, addresses of these two are NOT relative to + * channel struct on NV84+, and can be anywhere in VRAM, + * but we stuff them inside the channel struct anyway for + * simplicity. */ + ch->ramfc = nv50_chan_iobj_new(ch, 0x100); + ch->cache = pscnv_mem_alloc(vs->dev, 0x1000, PSCNV_GEM_CONTIG, + 0, 0xf1f0cace); + if (!ch->cache) { + spin_lock_irqsave(&dev_priv->chan->ch_lock, flags); + ch->handle = 0; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + pscnv_mem_free(ch->bo); + return -ENOMEM; + } + } + if (dev_priv->chipset != 0x50) { + nv_wr32(vs->dev, 0x2600 + ch->cid * 4, (ch->bo->start + ch->ramfc) >> 8); + } else { + nv_wr32(vs->dev, 0x2600 + ch->cid * 4, ch->bo->start >> 12); + } + } + dev_priv->vm->bar_flush(vs->dev); + return 0; +} + +int +nv50_chan_iobj_new(struct pscnv_chan *ch, uint32_t size) { + /* XXX: maybe do this "properly" one day? + * + * Why we don't implement _del for instance objects: + * - Usually, bounded const number of them is allocated + * for any given channel, and the used set doesn't change + * much during channel's lifetime + * - Since instance objects are stored inside the main + * VO of the channel, the storage will be freed on channel + * close anyway + * - We cannot easily tell what objects are currently in use + * by PGRAPH and maybe other execution engines -- the user + * could cheat us. Caching doesn't help either. + */ + int res; + size += 0xf; + size &= ~0xf; + spin_lock(&ch->instlock); + if (ch->instpos + size > ch->bo->size) { + spin_unlock(&ch->instlock); + return 0; + } + res = ch->instpos; + ch->instpos += size; + spin_unlock(&ch->instlock); + return res; +} + +/* XXX: we'll possibly want to break down type and/or add mysterious flags5 + * when we know more. */ +int +nv50_chan_dmaobj_new(struct pscnv_chan *ch, uint32_t type, uint64_t start, uint64_t size) { + struct drm_device *dev = ch->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint64_t end = start + size - 1; + int res = nv50_chan_iobj_new (ch, 0x18); + if (!res) + return 0; + + nv_wv32(ch->bo, res + 0x00, type); + nv_wv32(ch->bo, res + 0x04, end); + nv_wv32(ch->bo, res + 0x08, start); + nv_wv32(ch->bo, res + 0x0c, (end >> 32) << 24 | (start >> 32)); + nv_wv32(ch->bo, res + 0x10, 0); + nv_wv32(ch->bo, res + 0x14, 0x80000); + dev_priv->vm->bar_flush(dev); + + return res; +} + +void nv50_chan_free(struct pscnv_chan *ch) { + struct drm_nouveau_private *dev_priv = ch->dev->dev_private; + unsigned long flags; + spin_lock_irqsave(&dev_priv->chan->ch_lock, flags); + ch->handle = 0; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + pscnv_mem_free(ch->bo); + if (ch->cache) + pscnv_mem_free(ch->cache); + mutex_lock(&ch->vspace->lock); + list_del(&ch->vspace_list); + mutex_unlock(&ch->vspace->lock); +} + +void +nv50_chan_takedown(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv50_chan_engine *che = nv50_ch(dev_priv->chan); + kfree(che); +} + +int +nv50_chan_init(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv50_chan_engine *che = kzalloc(sizeof *che, GFP_KERNEL); + if (!che) { + NV_ERROR(dev, "CH: Couldn't alloc engine\n"); + return -ENOMEM; + } + che->base.takedown = nv50_chan_takedown; + che->base.do_chan_new = nv50_chan_new; + che->base.do_chan_free = nv50_chan_free; + dev_priv->chan = &che->base; + spin_lock_init(&dev_priv->chan->ch_lock); + dev_priv->chan->ch_min = 1; + dev_priv->chan->ch_max = 126; + return 0; +} diff --git a/driver/pscnv/nv50_chan.h b/driver/pscnv/nv50_chan.h new file mode 100644 index 00000000..8b3556ab --- /dev/null +++ b/driver/pscnv/nv50_chan.h @@ -0,0 +1,20 @@ +#ifndef __NV50_CHAN_H__ +#define __NV50_CHAN_H__ + +#include "drmP.h" +#include "drm.h" +#include "pscnv_chan.h" + +#define NV50_CHAN_PD 0x1400 +#define NV84_CHAN_PD 0x0200 + +#define nv50_ch(x) container_of(x, struct nv50_chan_engine, base) + +struct nv50_chan_engine { + struct pscnv_chan_engine base; +}; + +extern int nv50_chan_iobj_new(struct pscnv_chan *, uint32_t size); +extern int nv50_chan_dmaobj_new(struct pscnv_chan *, uint32_t type, uint64_t start, uint64_t size); + +#endif /* __NV50_CHAN_H__ */ diff --git a/driver/pscnv/nv50_crtc.c b/driver/pscnv/nv50_crtc.c new file mode 100644 index 00000000..1443e9a9 --- /dev/null +++ b/driver/pscnv/nv50_crtc.c @@ -0,0 +1,812 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include "drmP.h" +#include "drm_mode.h" +#include "drm_crtc_helper.h" + +#define NOUVEAU_DMA_DEBUG (nouveau_reg_debug & NOUVEAU_REG_DEBUG_EVO) +#include "nouveau_reg.h" +#include "nouveau_drv.h" +#include "nouveau_hw.h" +#include "nouveau_encoder.h" +#include "nouveau_crtc.h" +#include "nouveau_fb.h" +#include "nouveau_dma.h" +#include "nouveau_connector.h" +#include "nv50_display.h" +#include "pscnv_vm.h" +#include "pscnv_kapi.h" + +static void +nv50_crtc_lut_load(struct drm_crtc *crtc) +{ + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + int i; + uint16_t r, g, b; + + NV_DEBUG_KMS(crtc->dev, "\n"); + + for (i = 0; i < 256; i++) { + r = nv_crtc->lut.r[i] >> 2; + g = nv_crtc->lut.g[i] >> 2; + b = nv_crtc->lut.b[i] >> 2; + nv_wv32(nv_crtc->lut.nvbo, 8*i, r | g << 16); + nv_wv32(nv_crtc->lut.nvbo, 8*i + 4, b); + } + + if (nv_crtc->lut.depth == 30) { + nv_wv32(nv_crtc->lut.nvbo, 8*i, r | g << 16); + nv_wv32(nv_crtc->lut.nvbo, 8*i + 4, b); + } +} + +int +nv50_crtc_blank(struct nouveau_crtc *nv_crtc, bool blanked) +{ + struct drm_device *dev = nv_crtc->base.dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + int index = nv_crtc->index, ret; + + NV_DEBUG_KMS(dev, "index %d\n", nv_crtc->index); + NV_DEBUG_KMS(dev, "%s\n", blanked ? "blanked" : "unblanked"); + + if (blanked) { + nv_crtc->cursor.hide(nv_crtc, false); + + ret = RING_SPACE(evo, dev_priv->chipset != 0x50 ? 7 : 5); + if (ret) { + NV_ERROR(dev, "no space while blanking crtc\n"); + return ret; + } + BEGIN_RING(evo, 0, NV50_EVO_CRTC(index, CLUT_MODE), 2); + OUT_RING(evo, NV50_EVO_CRTC_CLUT_MODE_BLANK); + OUT_RING(evo, 0); + if (dev_priv->chipset != 0x50) { + BEGIN_RING(evo, 0, NV84_EVO_CRTC(index, CLUT_DMA), 1); + OUT_RING(evo, NV84_EVO_CRTC_CLUT_DMA_HANDLE_NONE); + } + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(index, FB_DMA), 1); + OUT_RING(evo, NV50_EVO_CRTC_FB_DMA_HANDLE_NONE); + } else { + if (nv_crtc->cursor.visible) + nv_crtc->cursor.show(nv_crtc, false); + else + nv_crtc->cursor.hide(nv_crtc, false); + + ret = RING_SPACE(evo, dev_priv->chipset != 0x50 ? 10 : 8); + if (ret) { + NV_ERROR(dev, "no space while unblanking crtc\n"); + return ret; + } + BEGIN_RING(evo, 0, NV50_EVO_CRTC(index, CLUT_MODE), 2); + OUT_RING(evo, nv_crtc->lut.depth == 8 ? + NV50_EVO_CRTC_CLUT_MODE_OFF : + NV50_EVO_CRTC_CLUT_MODE_ON); + OUT_RING(evo, nv_crtc->lut.nvbo->start >> 8); + if (dev_priv->chipset != 0x50) { + BEGIN_RING(evo, 0, NV84_EVO_CRTC(index, CLUT_DMA), 1); + OUT_RING(evo, NvEvoVRAM); + } + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(index, FB_OFFSET), 2); + OUT_RING(evo, nv_crtc->fb.offset >> 8); + OUT_RING(evo, 0); + BEGIN_RING(evo, 0, NV50_EVO_CRTC(index, FB_DMA), 1); + if (dev_priv->chipset != 0x50) { + if (nv_crtc->fb.tile_flags == 0xfe) + OUT_RING(evo, NvEvoFE); + else + if (nv_crtc->fb.tile_flags == 0x7a) + OUT_RING(evo, NvEvoFB32); + else + if (nv_crtc->fb.tile_flags == 0x70) + OUT_RING(evo, NvEvoFB16); + else + OUT_RING(evo, NvEvoVRAM); + } else { + OUT_RING(evo, NvEvoVRAM); + } + } + + nv_crtc->fb.blanked = blanked; + return 0; +} + +static int +nv50_crtc_set_dither(struct nouveau_crtc *nv_crtc, bool on, bool update) +{ + struct drm_device *dev = nv_crtc->base.dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + int ret; + + NV_DEBUG_KMS(dev, "\n"); + + ret = RING_SPACE(evo, 2 + (update ? 2 : 0)); + if (ret) { + NV_ERROR(dev, "no space while setting dither\n"); + return ret; + } + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, DITHER_CTRL), 1); + if (on) + OUT_RING(evo, NV50_EVO_CRTC_DITHER_CTRL_ON); + else + OUT_RING(evo, NV50_EVO_CRTC_DITHER_CTRL_OFF); + + if (update) { + BEGIN_RING(evo, 0, NV50_EVO_UPDATE, 1); + OUT_RING(evo, 0); + FIRE_RING(evo); + } + + return 0; +} + +struct nouveau_connector * +nouveau_crtc_connector_get(struct nouveau_crtc *nv_crtc) +{ + struct drm_device *dev = nv_crtc->base.dev; + struct drm_connector *connector; + struct drm_crtc *crtc = to_drm_crtc(nv_crtc); + + /* The safest approach is to find an encoder with the right crtc, that + * is also linked to a connector. */ + list_for_each_entry(connector, &dev->mode_config.connector_list, head) { + if (connector->encoder) + if (connector->encoder->crtc == crtc) + return nouveau_connector(connector); + } + + return NULL; +} + +static int +nv50_crtc_set_scale(struct nouveau_crtc *nv_crtc, int scaling_mode, bool update) +{ + struct nouveau_connector *nv_connector = + nouveau_crtc_connector_get(nv_crtc); + struct drm_device *dev = nv_crtc->base.dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + struct drm_display_mode *native_mode = NULL; + struct drm_display_mode *mode = &nv_crtc->base.mode; + uint32_t outX, outY, horiz, vert; + int ret; + + NV_DEBUG_KMS(dev, "\n"); + + switch (scaling_mode) { + case DRM_MODE_SCALE_NONE: + break; + default: + if (!nv_connector || !nv_connector->native_mode) { + NV_ERROR(dev, "No native mode, forcing panel scaling\n"); + scaling_mode = DRM_MODE_SCALE_NONE; + } else { + native_mode = nv_connector->native_mode; + } + break; + } + + switch (scaling_mode) { + case DRM_MODE_SCALE_ASPECT: + horiz = (native_mode->hdisplay << 19) / mode->hdisplay; + vert = (native_mode->vdisplay << 19) / mode->vdisplay; + + if (vert > horiz) { + outX = (mode->hdisplay * horiz) >> 19; + outY = (mode->vdisplay * horiz) >> 19; + } else { + outX = (mode->hdisplay * vert) >> 19; + outY = (mode->vdisplay * vert) >> 19; + } + break; + case DRM_MODE_SCALE_FULLSCREEN: + outX = native_mode->hdisplay; + outY = native_mode->vdisplay; + break; + case DRM_MODE_SCALE_CENTER: + case DRM_MODE_SCALE_NONE: + default: + outX = mode->hdisplay; + outY = mode->vdisplay; + break; + } + + ret = RING_SPACE(evo, update ? 7 : 5); + if (ret) + return ret; + + /* Got a better name for SCALER_ACTIVE? */ + /* One day i've got to really figure out why this is needed. */ + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, SCALE_CTRL), 1); + if ((mode->flags & DRM_MODE_FLAG_DBLSCAN) || + (mode->flags & DRM_MODE_FLAG_INTERLACE) || + mode->hdisplay != outX || mode->vdisplay != outY) { + OUT_RING(evo, NV50_EVO_CRTC_SCALE_CTRL_ACTIVE); + } else { + OUT_RING(evo, NV50_EVO_CRTC_SCALE_CTRL_INACTIVE); + } + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, SCALE_RES1), 2); + OUT_RING(evo, outY << 16 | outX); + OUT_RING(evo, outY << 16 | outX); + + if (update) { + BEGIN_RING(evo, 0, NV50_EVO_UPDATE, 1); + OUT_RING(evo, 0); + FIRE_RING(evo); + } + + return 0; +} + +int +nv50_crtc_set_clock(struct drm_device *dev, int head, int pclk) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct pll_lims pll; + uint32_t reg1, reg2; + int ret, N1, M1, N2, M2, P; + + ret = get_pll_limits(dev, PLL_VPLL0 + head, &pll); + if (ret) + return ret; + + if (pll.vco2.maxfreq) { + ret = nv50_calc_pll(dev, &pll, pclk, &N1, &M1, &N2, &M2, &P); + if (ret <= 0) + return 0; + + NV_DEBUG(dev, "pclk %d out %d NM1 %d %d NM2 %d %d P %d\n", + pclk, ret, N1, M1, N2, M2, P); + + reg1 = nv_rd32(dev, pll.reg + 4) & 0xff00ff00; + reg2 = nv_rd32(dev, pll.reg + 8) & 0x8000ff00; + nv_wr32(dev, pll.reg + 0, 0x10000611); + nv_wr32(dev, pll.reg + 4, reg1 | (M1 << 16) | N1); + nv_wr32(dev, pll.reg + 8, reg2 | (P << 28) | (M2 << 16) | N2); + } else + if (dev_priv->chipset < NV_C0) { + ret = nv50_calc_pll2(dev, &pll, pclk, &N1, &N2, &M1, &P); + if (ret <= 0) + return 0; + + NV_DEBUG(dev, "pclk %d out %d N %d fN 0x%04x M %d P %d\n", + pclk, ret, N1, N2, M1, P); + + reg1 = nv_rd32(dev, pll.reg + 4) & 0xffc00000; + nv_wr32(dev, pll.reg + 0, 0x50000610); + nv_wr32(dev, pll.reg + 4, reg1 | (P << 16) | (M1 << 8) | N1); + nv_wr32(dev, pll.reg + 8, N2); + } else { + ret = nv50_calc_pll2(dev, &pll, pclk, &N1, &N2, &M1, &P); + if (ret <= 0) + return 0; + + NV_DEBUG(dev, "pclk %d out %d N %d fN 0x%04x M %d P %d\n", + pclk, ret, N1, N2, M1, P); + + nv_mask(dev, pll.reg + 0x0c, 0x00000000, 0x00000100); + nv_wr32(dev, pll.reg + 0x04, (P << 16) | (N1 << 8) | M1); + nv_wr32(dev, pll.reg + 0x10, N2 << 16); + } + + return 0; +} + +static void +nv50_crtc_destroy(struct drm_crtc *crtc) +{ + struct drm_device *dev; + struct nouveau_crtc *nv_crtc; + + if (!crtc) + return; + + dev = crtc->dev; + nv_crtc = nouveau_crtc(crtc); + + NV_DEBUG_KMS(dev, "\n"); + + drm_crtc_cleanup(&nv_crtc->base); + + nv50_cursor_fini(nv_crtc); + + pscnv_mem_free(nv_crtc->lut.nvbo); + pscnv_mem_free(nv_crtc->cursor.nvbo); + + kfree(nv_crtc->mode); + kfree(nv_crtc); +} + +int +nv50_crtc_cursor_set(struct drm_crtc *crtc, struct drm_file *file_priv, + uint32_t buffer_handle, uint32_t width, uint32_t height) +{ + struct drm_device *dev = crtc->dev; + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + struct pscnv_bo *cursor = NULL; + struct drm_gem_object *gem; + int ret = 0, i, mt; + + if (width != 64 || height != 64) + return -EINVAL; + + if (!buffer_handle) { + nv_crtc->cursor.hide(nv_crtc, true); + return 0; + } + + gem = drm_gem_object_lookup(dev, file_priv, buffer_handle); + if (!gem) + return -EINVAL; + cursor = gem->driver_private; + + mt = cursor->flags & PSCNV_GEM_MEMTYPE_MASK; + if (mt != PSCNV_GEM_VRAM_SMALL && mt != PSCNV_GEM_VRAM_LARGE) { + drm_gem_object_unreference_unlocked(gem); + return -EINVAL; + } + + if (!(cursor->flags & PSCNV_GEM_CONTIG)) { + drm_gem_object_unreference_unlocked(gem); + return -EINVAL; + } + + /* The simple will do for now. */ + for (i = 0; i < 64 * 64; i++) + nv_wv32(nv_crtc->cursor.nvbo, i*4, nv_rv32(cursor, i*4)); + + nv_crtc->cursor.set_offset(nv_crtc, nv_crtc->cursor.nvbo->start); + nv_crtc->cursor.show(nv_crtc, true); + + drm_gem_object_unreference_unlocked(gem); + return ret; +} + +int +nv50_crtc_cursor_move(struct drm_crtc *crtc, int x, int y) +{ + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + + nv_crtc->cursor.set_pos(nv_crtc, x, y); + return 0; +} + +#ifdef PSCNV_KAPI_GAMMA_SET_5 +static void +nv50_crtc_gamma_set(struct drm_crtc *crtc, u16 *r, u16 *g, u16 *b, + uint32_t size) +{ + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + int i; + + if (size != 256) + return; + + for (i = 0; i < 256; i++) { + nv_crtc->lut.r[i] = r[i]; + nv_crtc->lut.g[i] = g[i]; + nv_crtc->lut.b[i] = b[i]; + } + + /* We need to know the depth before we upload, but it's possible to + * get called before a framebuffer is bound. If this is the case, + * mark the lut values as dirty by setting depth==0, and it'll be + * uploaded on the first mode_set_base() + */ + if (!nv_crtc->base.fb) { + nv_crtc->lut.depth = 0; + return; + } + + nv50_crtc_lut_load(crtc); +} +#else +#ifdef PSCNV_KAPI_GAMMA_SET_6 +static void +nv50_crtc_gamma_set(struct drm_crtc *crtc, u16 *r, u16 *g, u16 *b, + uint32_t start, uint32_t size) +{ + int end = (start + size > 256) ? 256 : start + size, i; + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + for (i = start; i < end; i++) { + nv_crtc->lut.r[i] = r[i]; + nv_crtc->lut.g[i] = g[i]; + nv_crtc->lut.b[i] = b[i]; + } + + /* We need to know the depth before we upload, but it's possible to + * get called before a framebuffer is bound. If this is the case, + * mark the lut values as dirty by setting depth==0, and it'll be + * uploaded on the first mode_set_base() + */ + if (!nv_crtc->base.fb) { + nv_crtc->lut.depth = 0; + return; + } + + nv50_crtc_lut_load(crtc); +} +#else +#error cannot determine gamma_set API +#endif +#endif + +static void +nv50_crtc_save(struct drm_crtc *crtc) +{ + NV_ERROR(crtc->dev, "!!\n"); +} + +static void +nv50_crtc_restore(struct drm_crtc *crtc) +{ + NV_ERROR(crtc->dev, "!!\n"); +} + +static const struct drm_crtc_funcs nv50_crtc_funcs = { + .save = nv50_crtc_save, + .restore = nv50_crtc_restore, + .cursor_set = nv50_crtc_cursor_set, + .cursor_move = nv50_crtc_cursor_move, + .gamma_set = nv50_crtc_gamma_set, + .set_config = drm_crtc_helper_set_config, + .destroy = nv50_crtc_destroy, +}; + +static void +nv50_crtc_dpms(struct drm_crtc *crtc, int mode) +{ +} + +static void +nv50_crtc_prepare(struct drm_crtc *crtc) +{ + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + struct drm_device *dev = crtc->dev; + + NV_DEBUG_KMS(dev, "index %d\n", nv_crtc->index); + + nv50_crtc_blank(nv_crtc, true); +} + +static void +nv50_crtc_commit(struct drm_crtc *crtc) +{ + struct drm_device *dev = crtc->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + int ret; + + NV_DEBUG_KMS(dev, "index %d\n", nv_crtc->index); + + nv50_crtc_blank(nv_crtc, false); + + ret = RING_SPACE(evo, 2); + if (ret) { + NV_ERROR(dev, "no space while committing crtc\n"); + return; + } + BEGIN_RING(evo, 0, NV50_EVO_UPDATE, 1); + OUT_RING (evo, 0); + FIRE_RING (evo); +} + +static bool +nv50_crtc_mode_fixup(struct drm_crtc *crtc, struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode) +{ + return true; +} + +static int +nv50_crtc_do_mode_set_base(struct drm_crtc *crtc, int x, int y, + struct drm_framebuffer *old_fb, bool update) +{ + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + struct drm_device *dev = nv_crtc->base.dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + struct drm_framebuffer *drm_fb = nv_crtc->base.fb; + struct nouveau_framebuffer *fb = nouveau_framebuffer(drm_fb); + int ret, format, mt; + + NV_DEBUG_KMS(dev, "index %d\n", nv_crtc->index); + + switch (drm_fb->depth) { + case 8: + format = NV50_EVO_CRTC_FB_DEPTH_8; + break; + case 15: + format = NV50_EVO_CRTC_FB_DEPTH_15; + break; + case 16: + format = NV50_EVO_CRTC_FB_DEPTH_16; + break; + case 24: + case 32: + format = NV50_EVO_CRTC_FB_DEPTH_24; + break; + case 30: + format = NV50_EVO_CRTC_FB_DEPTH_30; + break; + default: + NV_ERROR(dev, "unknown depth %d\n", drm_fb->depth); + return -EINVAL; + } + + if (!(fb->nvbo->flags & PSCNV_GEM_CONTIG)) + return -EINVAL; + + if (fb->nvbo->tile_flags && fb->nvbo->user[0] > 5) + return -EINVAL; + + /* XXX: verify object size */ + + mt = fb->nvbo->flags & PSCNV_GEM_MEMTYPE_MASK; + if (mt != PSCNV_GEM_VRAM_SMALL && mt != PSCNV_GEM_VRAM_LARGE) + return -EINVAL; + + nv_crtc->fb.offset = fb->nvbo->start; + nv_crtc->fb.tile_flags = fb->nvbo->tile_flags; + nv_crtc->fb.cpp = drm_fb->bits_per_pixel / 8; + if (!nv_crtc->fb.blanked && dev_priv->chipset != 0x50) { + ret = RING_SPACE(evo, 2); + if (ret) + return ret; + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, FB_DMA), 1); + if (nv_crtc->fb.tile_flags == 0xfe) + OUT_RING(evo, NvEvoFE); + else + if (nv_crtc->fb.tile_flags == 0x7a) + OUT_RING(evo, NvEvoFB32); + else + if (nv_crtc->fb.tile_flags == 0x70) + OUT_RING(evo, NvEvoFB16); + else + OUT_RING(evo, NvEvoVRAM); + } + + ret = RING_SPACE(evo, 12); + if (ret) + return ret; + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, FB_OFFSET), 5); + OUT_RING(evo, nv_crtc->fb.offset >> 8); + OUT_RING(evo, 0); + OUT_RING(evo, (drm_fb->height << 16) | drm_fb->width); + if (!nv_crtc->fb.tile_flags) { + OUT_RING(evo, drm_fb->pitch | (1 << 20)); + } else { + OUT_RING(evo, ((drm_fb->pitch / 4) << 4) | + fb->nvbo->user[0]); + } + if (dev_priv->chipset == 0x50) + OUT_RING(evo, (fb->nvbo->tile_flags << 16) | format); + else + OUT_RING(evo, format); + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, CLUT_MODE), 1); + OUT_RING(evo, fb->base.depth == 8 ? + NV50_EVO_CRTC_CLUT_MODE_OFF : NV50_EVO_CRTC_CLUT_MODE_ON); + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, COLOR_CTRL), 1); + OUT_RING(evo, NV50_EVO_CRTC_COLOR_CTRL_COLOR); + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, FB_POS), 1); + OUT_RING(evo, (y << 16) | x); + + if (nv_crtc->lut.depth != fb->base.depth) { + nv_crtc->lut.depth = fb->base.depth; + nv50_crtc_lut_load(crtc); + } + + if (update) { + ret = RING_SPACE(evo, 2); + if (ret) + return ret; + BEGIN_RING(evo, 0, NV50_EVO_UPDATE, 1); + OUT_RING(evo, 0); + FIRE_RING(evo); + } + + return 0; +} + +static int +nv50_crtc_mode_set(struct drm_crtc *crtc, struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode, int x, int y, + struct drm_framebuffer *old_fb) +{ + struct drm_device *dev = crtc->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); + struct nouveau_connector *nv_connector = NULL; + uint32_t hsync_dur, vsync_dur, hsync_start_to_end, vsync_start_to_end; + uint32_t hunk1, vunk1, vunk2a, vunk2b; + int ret; + + /* Find the connector attached to this CRTC */ + nv_connector = nouveau_crtc_connector_get(nv_crtc); + + *nv_crtc->mode = *adjusted_mode; + + NV_DEBUG_KMS(dev, "index %d\n", nv_crtc->index); + + hsync_dur = adjusted_mode->hsync_end - adjusted_mode->hsync_start; + vsync_dur = adjusted_mode->vsync_end - adjusted_mode->vsync_start; + hsync_start_to_end = adjusted_mode->htotal - adjusted_mode->hsync_start; + vsync_start_to_end = adjusted_mode->vtotal - adjusted_mode->vsync_start; + /* I can't give this a proper name, anyone else can? */ + hunk1 = adjusted_mode->htotal - + adjusted_mode->hsync_start + adjusted_mode->hdisplay; + vunk1 = adjusted_mode->vtotal - + adjusted_mode->vsync_start + adjusted_mode->vdisplay; + /* Another strange value, this time only for interlaced adjusted_modes. */ + vunk2a = 2 * adjusted_mode->vtotal - + adjusted_mode->vsync_start + adjusted_mode->vdisplay; + vunk2b = adjusted_mode->vtotal - + adjusted_mode->vsync_start + adjusted_mode->vtotal; + + if (adjusted_mode->flags & DRM_MODE_FLAG_INTERLACE) { + vsync_dur /= 2; + vsync_start_to_end /= 2; + vunk1 /= 2; + vunk2a /= 2; + vunk2b /= 2; + /* magic */ + if (adjusted_mode->flags & DRM_MODE_FLAG_DBLSCAN) { + vsync_start_to_end -= 1; + vunk1 -= 1; + vunk2a -= 1; + vunk2b -= 1; + } + } + + ret = RING_SPACE(evo, 17); + if (ret) + return ret; + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, CLOCK), 2); + OUT_RING(evo, adjusted_mode->clock | 0x800000); + OUT_RING(evo, (adjusted_mode->flags & DRM_MODE_FLAG_INTERLACE) ? 2 : 0); + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, DISPLAY_START), 5); + OUT_RING(evo, 0); + OUT_RING(evo, (adjusted_mode->vtotal << 16) | adjusted_mode->htotal); + OUT_RING(evo, (vsync_dur - 1) << 16 | (hsync_dur - 1)); + OUT_RING(evo, (vsync_start_to_end - 1) << 16 | + (hsync_start_to_end - 1)); + OUT_RING(evo, (vunk1 - 1) << 16 | (hunk1 - 1)); + + if (adjusted_mode->flags & DRM_MODE_FLAG_INTERLACE) { + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, UNK0824), 1); + OUT_RING(evo, (vunk2b - 1) << 16 | (vunk2a - 1)); + } else { + OUT_RING(evo, 0); + OUT_RING(evo, 0); + } + + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, UNK082C), 1); + OUT_RING(evo, 0); + + /* This is the actual resolution of the mode. */ + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, REAL_RES), 1); + OUT_RING(evo, (mode->vdisplay << 16) | mode->hdisplay); + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, SCALE_CENTER_OFFSET), 1); + OUT_RING(evo, NV50_EVO_CRTC_SCALE_CENTER_OFFSET_VAL(0, 0)); + + nv_crtc->set_dither(nv_crtc, nv_connector->use_dithering, false); + nv_crtc->set_scale(nv_crtc, nv_connector->scaling_mode, false); + + return nv50_crtc_do_mode_set_base(crtc, x, y, old_fb, false); +} + +static int +nv50_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y, + struct drm_framebuffer *old_fb) +{ + return nv50_crtc_do_mode_set_base(crtc, x, y, old_fb, true); +} + +static const struct drm_crtc_helper_funcs nv50_crtc_helper_funcs = { + .dpms = nv50_crtc_dpms, + .prepare = nv50_crtc_prepare, + .commit = nv50_crtc_commit, + .mode_fixup = nv50_crtc_mode_fixup, + .mode_set = nv50_crtc_mode_set, + .mode_set_base = nv50_crtc_mode_set_base, + .load_lut = nv50_crtc_lut_load, +}; + +int +nv50_crtc_create(struct drm_device *dev, int index) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_crtc *nv_crtc = NULL; + int i; + + NV_DEBUG_KMS(dev, "\n"); + + nv_crtc = kzalloc(sizeof(*nv_crtc), GFP_KERNEL); + if (!nv_crtc) + return -ENOMEM; + + nv_crtc->mode = kzalloc(sizeof(*nv_crtc->mode), GFP_KERNEL); + if (!nv_crtc->mode) { + kfree(nv_crtc); + return -ENOMEM; + } + + /* Default CLUT parameters, will be activated on the hw upon + * first mode set. + */ + for (i = 0; i < 256; i++) { + nv_crtc->lut.r[i] = i << 8; + nv_crtc->lut.g[i] = i << 8; + nv_crtc->lut.b[i] = i << 8; + } + nv_crtc->lut.depth = 0; + + nv_crtc->lut.nvbo = pscnv_mem_alloc(dev, 4096, PSCNV_GEM_CONTIG, 0, 0xd1517); + + if (!nv_crtc->lut.nvbo) { + kfree(nv_crtc->mode); + kfree(nv_crtc); + return -ENOMEM; + } + + dev_priv->vm->map_kernel(nv_crtc->lut.nvbo); + + nv_crtc->index = index; + + /* set function pointers */ + nv_crtc->set_dither = nv50_crtc_set_dither; + nv_crtc->set_scale = nv50_crtc_set_scale; + + drm_crtc_init(dev, &nv_crtc->base, &nv50_crtc_funcs); + drm_crtc_helper_add(&nv_crtc->base, &nv50_crtc_helper_funcs); + drm_mode_crtc_set_gamma_size(&nv_crtc->base, 256); + + nv_crtc->cursor.nvbo = pscnv_mem_alloc(dev, 64*64*4, PSCNV_GEM_CONTIG, 0, 0xd15c); + if (!nv_crtc->cursor.nvbo) { + pscnv_mem_free(nv_crtc->lut.nvbo); + kfree(nv_crtc->mode); + kfree(nv_crtc); + return -ENOMEM; + } + + nv50_cursor_init(nv_crtc); + return 0; +} diff --git a/driver/pscnv/nv50_cursor.c b/driver/pscnv/nv50_cursor.c new file mode 100644 index 00000000..6cd33a09 --- /dev/null +++ b/driver/pscnv/nv50_cursor.c @@ -0,0 +1,158 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include "drmP.h" +#include "drm_mode.h" + +#define NOUVEAU_DMA_DEBUG (nouveau_reg_debug & NOUVEAU_REG_DEBUG_EVO) +#include "nouveau_reg.h" +#include "nouveau_drv.h" +#include "nouveau_crtc.h" +#include "nouveau_dma.h" +#include "nv50_display.h" + +static void +nv50_cursor_show(struct nouveau_crtc *nv_crtc, bool update) +{ + struct drm_nouveau_private *dev_priv = nv_crtc->base.dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + struct drm_device *dev = nv_crtc->base.dev; + int ret; + + NV_DEBUG_KMS(dev, "\n"); + + if (update && nv_crtc->cursor.visible) + return; + + ret = RING_SPACE(evo, (dev_priv->chipset != 0x50 ? 5 : 3) + update * 2); + if (ret) { + NV_ERROR(dev, "no space while unhiding cursor\n"); + return; + } + + if (dev_priv->chipset != 0x50) { + BEGIN_RING(evo, 0, NV84_EVO_CRTC(nv_crtc->index, CURSOR_DMA), 1); + OUT_RING(evo, NvEvoVRAM); + } + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, CURSOR_CTRL), 2); + OUT_RING(evo, NV50_EVO_CRTC_CURSOR_CTRL_SHOW); + OUT_RING(evo, nv_crtc->cursor.offset >> 8); + + if (update) { + BEGIN_RING(evo, 0, NV50_EVO_UPDATE, 1); + OUT_RING(evo, 0); + FIRE_RING(evo); + nv_crtc->cursor.visible = true; + } +} + +static void +nv50_cursor_hide(struct nouveau_crtc *nv_crtc, bool update) +{ + struct drm_nouveau_private *dev_priv = nv_crtc->base.dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + struct drm_device *dev = nv_crtc->base.dev; + int ret; + + NV_DEBUG_KMS(dev, "\n"); + + if (update && !nv_crtc->cursor.visible) + return; + + ret = RING_SPACE(evo, (dev_priv->chipset != 0x50 ? 5 : 3) + update * 2); + if (ret) { + NV_ERROR(dev, "no space while hiding cursor\n"); + return; + } + BEGIN_RING(evo, 0, NV50_EVO_CRTC(nv_crtc->index, CURSOR_CTRL), 2); + OUT_RING(evo, NV50_EVO_CRTC_CURSOR_CTRL_HIDE); + OUT_RING(evo, 0); + if (dev_priv->chipset != 0x50) { + BEGIN_RING(evo, 0, NV84_EVO_CRTC(nv_crtc->index, CURSOR_DMA), 1); + OUT_RING(evo, NV84_EVO_CRTC_CURSOR_DMA_HANDLE_NONE); + } + + if (update) { + BEGIN_RING(evo, 0, NV50_EVO_UPDATE, 1); + OUT_RING(evo, 0); + FIRE_RING(evo); + nv_crtc->cursor.visible = false; + } +} + +static void +nv50_cursor_set_pos(struct nouveau_crtc *nv_crtc, int x, int y) +{ + struct drm_device *dev = nv_crtc->base.dev; + + nv_crtc->cursor_saved_x = x; nv_crtc->cursor_saved_y = y; + nv_wr32(dev, NV50_PDISPLAY_CURSOR_USER_POS(nv_crtc->index), + ((y & 0xFFFF) << 16) | (x & 0xFFFF)); + /* Needed to make the cursor move. */ + nv_wr32(dev, NV50_PDISPLAY_CURSOR_USER_POS_CTRL(nv_crtc->index), 0); +} + +static void +nv50_cursor_set_offset(struct nouveau_crtc *nv_crtc, uint32_t offset) +{ + NV_DEBUG_KMS(nv_crtc->base.dev, "\n"); + if (offset == nv_crtc->cursor.offset) + return; + + nv_crtc->cursor.offset = offset; + if (nv_crtc->cursor.visible) { + nv_crtc->cursor.visible = false; + nv_crtc->cursor.show(nv_crtc, true); + } +} + +int +nv50_cursor_init(struct nouveau_crtc *nv_crtc) +{ + nv_crtc->cursor.set_offset = nv50_cursor_set_offset; + nv_crtc->cursor.set_pos = nv50_cursor_set_pos; + nv_crtc->cursor.hide = nv50_cursor_hide; + nv_crtc->cursor.show = nv50_cursor_show; + return 0; +} + +void +nv50_cursor_fini(struct nouveau_crtc *nv_crtc) +{ + struct drm_device *dev = nv_crtc->base.dev; + int idx = nv_crtc->index; + + NV_DEBUG_KMS(dev, "\n"); + + nv_wr32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(idx), 0); + if (!nv_wait(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(idx), + NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS, 0)) { + NV_ERROR(dev, "timeout: CURSOR_CTRL2_STATUS == 0\n"); + NV_ERROR(dev, "CURSOR_CTRL2 = 0x%08x\n", + nv_rd32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(idx))); + } +} + diff --git a/driver/pscnv/nv50_dac.c b/driver/pscnv/nv50_dac.c new file mode 100644 index 00000000..875414b0 --- /dev/null +++ b/driver/pscnv/nv50_dac.c @@ -0,0 +1,321 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include "drmP.h" +#include "drm_crtc_helper.h" + +#define NOUVEAU_DMA_DEBUG (nouveau_reg_debug & NOUVEAU_REG_DEBUG_EVO) +#include "nouveau_reg.h" +#include "nouveau_drv.h" +#include "nouveau_dma.h" +#include "nouveau_encoder.h" +#include "nouveau_connector.h" +#include "nouveau_crtc.h" +#include "nv50_display.h" + +static void +nv50_dac_disconnect(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + int ret; + + if (!nv_encoder->crtc) + return; + nv50_crtc_blank(nouveau_crtc(nv_encoder->crtc), true); + + NV_DEBUG_KMS(dev, "Disconnecting DAC %d\n", nv_encoder->or); + + ret = RING_SPACE(evo, 4); + if (ret) { + NV_ERROR(dev, "no space while disconnecting DAC\n"); + return; + } + BEGIN_RING(evo, 0, NV50_EVO_DAC(nv_encoder->or, MODE_CTRL), 1); + OUT_RING (evo, 0); + BEGIN_RING(evo, 0, NV50_EVO_UPDATE, 1); + OUT_RING (evo, 0); + + nv_encoder->crtc = NULL; +} + +static enum drm_connector_status +nv50_dac_detect(struct drm_encoder *encoder, struct drm_connector *connector) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + enum drm_connector_status status = connector_status_disconnected; + uint32_t dpms_state, load_pattern, load_state; + int or = nv_encoder->or; + + nv_wr32(dev, NV50_PDISPLAY_DAC_CLK_CTRL1(or), 0x00000001); + dpms_state = nv_rd32(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(or)); + + nv_wr32(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(or), + 0x00150000 | NV50_PDISPLAY_DAC_DPMS_CTRL_PENDING); + if (!nv_wait(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(or), + NV50_PDISPLAY_DAC_DPMS_CTRL_PENDING, 0)) { + NV_ERROR(dev, "timeout: DAC_DPMS_CTRL_PENDING(%d) == 0\n", or); + NV_ERROR(dev, "DAC_DPMS_CTRL(%d) = 0x%08x\n", or, + nv_rd32(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(or))); + return status; + } + + /* Use bios provided value if possible. */ + if (dev_priv->vbios.dactestval) { + load_pattern = dev_priv->vbios.dactestval; + NV_DEBUG_KMS(dev, "Using bios provided load_pattern of %d\n", + load_pattern); + } else { + load_pattern = 340; + NV_DEBUG_KMS(dev, "Using default load_pattern of %d\n", + load_pattern); + } + + nv_wr32(dev, NV50_PDISPLAY_DAC_LOAD_CTRL(or), + NV50_PDISPLAY_DAC_LOAD_CTRL_ACTIVE | load_pattern); + mdelay(45); /* give it some time to process */ + load_state = nv_rd32(dev, NV50_PDISPLAY_DAC_LOAD_CTRL(or)); + + nv_wr32(dev, NV50_PDISPLAY_DAC_LOAD_CTRL(or), 0); + nv_wr32(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(or), dpms_state | + NV50_PDISPLAY_DAC_DPMS_CTRL_PENDING); + + if ((load_state & NV50_PDISPLAY_DAC_LOAD_CTRL_PRESENT) == + NV50_PDISPLAY_DAC_LOAD_CTRL_PRESENT) + status = connector_status_connected; + + if (status == connector_status_connected) + NV_DEBUG_KMS(dev, "Load was detected on output with or %d\n", or); + else + NV_DEBUG_KMS(dev, "Load was not detected on output with or %d\n", or); + + return status; +} + +static void +nv50_dac_dpms(struct drm_encoder *encoder, int mode) +{ + struct drm_device *dev = encoder->dev; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + uint32_t val; + int or = nv_encoder->or; + + NV_DEBUG_KMS(dev, "or %d mode %d\n", or, mode); + + /* wait for it to be done */ + if (!nv_wait(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(or), + NV50_PDISPLAY_DAC_DPMS_CTRL_PENDING, 0)) { + NV_ERROR(dev, "timeout: DAC_DPMS_CTRL_PENDING(%d) == 0\n", or); + NV_ERROR(dev, "DAC_DPMS_CTRL(%d) = 0x%08x\n", or, + nv_rd32(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(or))); + return; + } + + val = nv_rd32(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(or)) & ~0x7F; + + if (mode != DRM_MODE_DPMS_ON) + val |= NV50_PDISPLAY_DAC_DPMS_CTRL_BLANKED; + + switch (mode) { + case DRM_MODE_DPMS_STANDBY: + val |= NV50_PDISPLAY_DAC_DPMS_CTRL_HSYNC_OFF; + break; + case DRM_MODE_DPMS_SUSPEND: + val |= NV50_PDISPLAY_DAC_DPMS_CTRL_VSYNC_OFF; + break; + case DRM_MODE_DPMS_OFF: + val |= NV50_PDISPLAY_DAC_DPMS_CTRL_OFF; + val |= NV50_PDISPLAY_DAC_DPMS_CTRL_HSYNC_OFF; + val |= NV50_PDISPLAY_DAC_DPMS_CTRL_VSYNC_OFF; + break; + default: + break; + } + + nv_wr32(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(or), val | + NV50_PDISPLAY_DAC_DPMS_CTRL_PENDING); +} + +static void +nv50_dac_save(struct drm_encoder *encoder) +{ + NV_ERROR(encoder->dev, "!!\n"); +} + +static void +nv50_dac_restore(struct drm_encoder *encoder) +{ + NV_ERROR(encoder->dev, "!!\n"); +} + +static bool +nv50_dac_mode_fixup(struct drm_encoder *encoder, struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct nouveau_connector *connector; + + NV_DEBUG_KMS(encoder->dev, "or %d\n", nv_encoder->or); + + connector = nouveau_encoder_connector_get(nv_encoder); + if (!connector) { + NV_ERROR(encoder->dev, "Encoder has no connector\n"); + return false; + } + + if (connector->scaling_mode != DRM_MODE_SCALE_NONE && + connector->native_mode) { + int id = adjusted_mode->base.id; + *adjusted_mode = *connector->native_mode; + adjusted_mode->base.id = id; + } + + return true; +} + +static void +nv50_dac_prepare(struct drm_encoder *encoder) +{ +} + +static void +nv50_dac_commit(struct drm_encoder *encoder) +{ +} + +static void +nv50_dac_mode_set(struct drm_encoder *encoder, struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + struct nouveau_crtc *crtc = nouveau_crtc(encoder->crtc); + uint32_t mode_ctl = 0, mode_ctl2 = 0; + int ret; + + NV_DEBUG_KMS(dev, "or %d type %d crtc %d\n", + nv_encoder->or, nv_encoder->dcb->type, crtc->index); + + nv50_dac_dpms(encoder, DRM_MODE_DPMS_ON); + + if (crtc->index == 1) + mode_ctl |= NV50_EVO_DAC_MODE_CTRL_CRTC1; + else + mode_ctl |= NV50_EVO_DAC_MODE_CTRL_CRTC0; + + /* Lacking a working tv-out, this is not a 100% sure. */ + if (nv_encoder->dcb->type == OUTPUT_ANALOG) + mode_ctl |= 0x40; + else + if (nv_encoder->dcb->type == OUTPUT_TV) + mode_ctl |= 0x100; + + if (adjusted_mode->flags & DRM_MODE_FLAG_NHSYNC) + mode_ctl2 |= NV50_EVO_DAC_MODE_CTRL2_NHSYNC; + + if (adjusted_mode->flags & DRM_MODE_FLAG_NVSYNC) + mode_ctl2 |= NV50_EVO_DAC_MODE_CTRL2_NVSYNC; + + ret = RING_SPACE(evo, 3); + if (ret) { + NV_ERROR(dev, "no space while connecting DAC\n"); + return; + } + BEGIN_RING(evo, 0, NV50_EVO_DAC(nv_encoder->or, MODE_CTRL), 2); + OUT_RING(evo, mode_ctl); + OUT_RING(evo, mode_ctl2); + + nv_encoder->crtc = encoder->crtc; +} + +static struct drm_crtc * +nv50_dac_crtc_get(struct drm_encoder *encoder) +{ + return nouveau_encoder(encoder)->crtc; +} + +static const struct drm_encoder_helper_funcs nv50_dac_helper_funcs = { + .dpms = nv50_dac_dpms, + .save = nv50_dac_save, + .restore = nv50_dac_restore, + .mode_fixup = nv50_dac_mode_fixup, + .prepare = nv50_dac_prepare, + .commit = nv50_dac_commit, + .mode_set = nv50_dac_mode_set, + .get_crtc = nv50_dac_crtc_get, + .detect = nv50_dac_detect, + .disable = nv50_dac_disconnect +}; + +static void +nv50_dac_destroy(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + + if (!encoder) + return; + + NV_DEBUG_KMS(encoder->dev, "\n"); + + drm_encoder_cleanup(encoder); + kfree(nv_encoder); +} + +static const struct drm_encoder_funcs nv50_dac_encoder_funcs = { + .destroy = nv50_dac_destroy, +}; + +int +nv50_dac_create(struct drm_connector *connector, struct dcb_entry *entry) +{ + struct nouveau_encoder *nv_encoder; + struct drm_encoder *encoder; + + nv_encoder = kzalloc(sizeof(*nv_encoder), GFP_KERNEL); + if (!nv_encoder) + return -ENOMEM; + encoder = to_drm_encoder(nv_encoder); + + nv_encoder->dcb = entry; + nv_encoder->or = ffs(entry->or) - 1; + + drm_encoder_init(connector->dev, encoder, &nv50_dac_encoder_funcs, + DRM_MODE_ENCODER_DAC); + drm_encoder_helper_add(encoder, &nv50_dac_helper_funcs); + + encoder->possible_crtcs = entry->heads; + encoder->possible_clones = 0; + + drm_mode_connector_attach_encoder(connector, encoder); + return 0; +} + diff --git a/driver/pscnv/nv50_display.c b/driver/pscnv/nv50_display.c new file mode 100644 index 00000000..616d3941 --- /dev/null +++ b/driver/pscnv/nv50_display.c @@ -0,0 +1,1124 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include "nv50_display.h" +#include "nouveau_crtc.h" +#include "nouveau_encoder.h" +#include "nouveau_connector.h" +#include "nouveau_fb.h" +#include "nouveau_dma.h" +#include "nouveau_fbcon.h" +#include "drm_crtc_helper.h" +#include "pscnv_vm.h" + +static inline int +nv50_sor_nr(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + if (dev_priv->chipset < 0x90 || + dev_priv->chipset == 0x92 || + dev_priv->chipset == 0xa0) + return 2; + + return 4; +} + +static void +nv50_evo_channel_del(struct nouveau_channel **pchan) +{ + struct nouveau_channel *chan = *pchan; + + if (!chan) + return; + *pchan = NULL; + + if (chan->pushbuf) + pscnv_mem_free(chan->pushbuf); + if (chan->evo_obj) + pscnv_mem_free(chan->evo_obj); + + kfree(chan); +} + +static int +nv50_evo_dmaobj_new(struct nouveau_channel *evo, uint32_t class, uint32_t name, + uint32_t tile_flags, uint32_t magic_flags, + uint32_t offset, uint32_t limit) +{ + struct drm_device *dev = evo->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + int ret; + + uint32_t inst = evo->evo_inst; + if (inst+0x20 > evo->evo_obj->size) + return -ENOMEM; + evo->evo_inst += 0x20; + + if ((ret = pscnv_ramht_insert(&evo->evo_ramht, name, inst << 10 | 2))) { + return ret; + evo->evo_inst -= 0x20; + } + + nv_wv32(evo->evo_obj, inst + 0x00, (tile_flags << 22) | (magic_flags << 16) | class); + nv_wv32(evo->evo_obj, inst + 0x04, limit); + nv_wv32(evo->evo_obj, inst + 0x08, offset); + nv_wv32(evo->evo_obj, inst + 0x0c, 0x00000000); + if (dev_priv->card_type >= NV_C0) { + nv_wv32(evo->evo_obj, inst + 0x10, 0x00000010); + nv_wv32(evo->evo_obj, inst + 0x14, tile_flags ? 0 : 0x20000); + } else { + nv_wv32(evo->evo_obj, inst + 0x10, 0x00000000); + nv_wv32(evo->evo_obj, inst + 0x14, 0x00010000); + } + dev_priv->vm->bar_flush(dev); + + return 0; +} + +static int +nv50_evo_channel_new(struct drm_device *dev, struct nouveau_channel **pchan) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *chan; + int ret; + int i; + + chan = kzalloc(sizeof(struct nouveau_channel), GFP_KERNEL); + if (!chan) + return -ENOMEM; + *pchan = chan; + + chan->id = -1; + chan->dev = dev; + chan->user_put = NV50_PDISPLAY_USER_PUT(0); + chan->user_get = NV50_PDISPLAY_USER_GET(0); + + chan->evo_obj = pscnv_mem_alloc(dev, 0x2000, PSCNV_GEM_CONTIG | PSCNV_GEM_VRAM_LARGE, 0, 0xd1501a7); + if (!chan->evo_obj) { + nv50_evo_channel_del(pchan); + NV_ERROR(dev, "Error allocating EVO channel memory\n"); + return -ENOMEM; + } + spin_lock_init(&chan->evo_ramht.lock); + chan->evo_ramht.bo = chan->evo_obj; + chan->evo_ramht.bits = 9; + chan->evo_ramht.offset = 0; + chan->evo_inst = 0x1000; + dev_priv->vm->map_kernel(chan->evo_obj); + for (i = 0; i < 0x1000; i += 4) + nv_wv32(chan->evo_obj, i, 0); + + if (dev_priv->chipset >= 0xc0) { + ret = nv50_evo_dmaobj_new(chan, 0x3d, NvEvoFE, 0xfe, 0x19, + 0, 0xffffffff); + if (ret) { + nv50_evo_channel_del(pchan); + return ret; + } + } else + if (dev_priv->chipset > 0x50) { + ret = nv50_evo_dmaobj_new(chan, 0x3d, NvEvoFB16, 0x70, 0x19, + 0, 0xffffffff); + if (ret) { + nv50_evo_channel_del(pchan); + return ret; + } + + + ret = nv50_evo_dmaobj_new(chan, 0x3d, NvEvoFB32, 0x7a, 0x19, + 0, 0xffffffff); + if (ret) { + nv50_evo_channel_del(pchan); + return ret; + } + } + + ret = nv50_evo_dmaobj_new(chan, 0x3d, NvEvoVRAM, 0, 0x19, + 0, dev_priv->vram_size); + if (ret) { + nv50_evo_channel_del(pchan); + return ret; + } + + chan->pushbuf = pscnv_mem_alloc(dev, 0x1000, PSCNV_GEM_CONTIG, 0, 0xd15f1f0); + if (!chan->pushbuf) { + NV_ERROR(dev, "Error creating EVO DMA push buffer: %d\n", ret); + nv50_evo_channel_del(pchan); + return -ENOMEM; + } + dev_priv->vm->map_kernel(chan->pushbuf); + chan->pushbuf_base = 0; + + return 0; +} + +int +nv50_display_early_init(struct drm_device *dev) +{ + return 0; +} + +void +nv50_display_late_takedown(struct drm_device *dev) +{ +} + +int +nv50_display_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_gpio_engine *pgpio = &dev_priv->engine.gpio; + struct nouveau_channel *evo = dev_priv->evo; + struct drm_connector *connector; + uint32_t val, ram_amount; + uint64_t start; + int ret, i; + + NV_DEBUG_KMS(dev, "\n"); + + nv_wr32(dev, 0x00610184, nv_rd32(dev, 0x00614004)); + /* + * I think the 0x006101XX range is some kind of main control area + * that enables things. + */ + /* CRTC? */ + for (i = 0; i < 2; i++) { + val = nv_rd32(dev, 0x00616100 + (i * 0x800)); + nv_wr32(dev, 0x00610190 + (i * 0x10), val); + val = nv_rd32(dev, 0x00616104 + (i * 0x800)); + nv_wr32(dev, 0x00610194 + (i * 0x10), val); + val = nv_rd32(dev, 0x00616108 + (i * 0x800)); + nv_wr32(dev, 0x00610198 + (i * 0x10), val); + val = nv_rd32(dev, 0x0061610c + (i * 0x800)); + nv_wr32(dev, 0x0061019c + (i * 0x10), val); + } + /* DAC */ + for (i = 0; i < 3; i++) { + val = nv_rd32(dev, 0x0061a000 + (i * 0x800)); + nv_wr32(dev, 0x006101d0 + (i * 0x04), val); + } + /* SOR */ + for (i = 0; i < nv50_sor_nr(dev); i++) { + val = nv_rd32(dev, 0x0061c000 + (i * 0x800)); + nv_wr32(dev, 0x006101e0 + (i * 0x04), val); + } + /* EXT */ + for (i = 0; i < 3; i++) { + val = nv_rd32(dev, 0x0061e000 + (i * 0x800)); + nv_wr32(dev, 0x006101f0 + (i * 0x04), val); + } + + for (i = 0; i < 3; i++) { + nv_wr32(dev, NV50_PDISPLAY_DAC_DPMS_CTRL(i), 0x00550000 | + NV50_PDISPLAY_DAC_DPMS_CTRL_PENDING); + nv_wr32(dev, NV50_PDISPLAY_DAC_CLK_CTRL1(i), 0x00000001); + } + + /* This used to be in crtc unblank, but seems out of place there. */ + nv_wr32(dev, NV50_PDISPLAY_UNK_380, 0); + /* RAM is clamped to 256 MiB. */ + ram_amount = dev_priv->vram_size; + NV_DEBUG_KMS(dev, "ram_amount %d\n", ram_amount); + if (ram_amount > 256*1024*1024) + ram_amount = 256*1024*1024; + + if (dev_priv->card_type < NV_C0) { + nv_wr32(dev, NV50_PDISPLAY_RAM_AMOUNT, ram_amount - 1); + nv_wr32(dev, NV50_PDISPLAY_UNK_388, 0x150000); + nv_wr32(dev, NV50_PDISPLAY_UNK_38C, 0); + } + + /* The precise purpose is unknown, i suspect it has something to do + * with text mode. + */ + if (nv_rd32(dev, NV50_PDISPLAY_INTR_1) & 0x100) { + nv_wr32(dev, NV50_PDISPLAY_INTR_1, 0x100); + nv_wr32(dev, 0x006194e8, nv_rd32(dev, 0x006194e8) & ~1); + if (!nv_wait(dev, 0x006194e8, 2, 0)) { + NV_ERROR(dev, "timeout: (0x6194e8 & 2) != 0\n"); + NV_ERROR(dev, "0x6194e8 = 0x%08x\n", + nv_rd32(dev, 0x6194e8)); + return -EBUSY; + } + } + + /* taken from nv bug #12637, attempts to un-wedge the hw if it's + * stuck in some unspecified state + */ + start = nv04_timer_read(dev); + nv_wr32(dev, NV50_PDISPLAY_CHANNEL_STAT(0), 0x2b00); + while ((val = nv_rd32(dev, NV50_PDISPLAY_CHANNEL_STAT(0))) & 0x1e0000) { + if ((val & 0x9f0000) == 0x20000) + nv_wr32(dev, NV50_PDISPLAY_CHANNEL_STAT(0), + val | 0x800000); + + if ((val & 0x3f0000) == 0x30000) + nv_wr32(dev, NV50_PDISPLAY_CHANNEL_STAT(0), + val | 0x200000); + + if (nv04_timer_read(dev) - start > 1000000000ULL) { + NV_ERROR(dev, "timeout: (0x610200 & 0x1e0000) != 0\n"); + NV_ERROR(dev, "0x610200 = 0x%08x\n", val); + return -EBUSY; + } + } + + nv_wr32(dev, NV50_PDISPLAY_CTRL_STATE, NV50_PDISPLAY_CTRL_STATE_ENABLE); + nv_wr32(dev, NV50_PDISPLAY_CHANNEL_STAT(0), 0x1000b03); + if (!nv_wait(dev, NV50_PDISPLAY_CHANNEL_STAT(0), + 0x40000000, 0x40000000)) { + NV_ERROR(dev, "timeout: (0x610200 & 0x40000000) == 0x40000000\n"); + NV_ERROR(dev, "0x610200 = 0x%08x\n", + nv_rd32(dev, NV50_PDISPLAY_CHANNEL_STAT(0))); + return -EBUSY; + } + + for (i = 0; i < 2; i++) { + nv_wr32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), 0x2000); + if (!nv_wait(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), + NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS, 0)) { + NV_ERROR(dev, "timeout: CURSOR_CTRL2_STATUS == 0\n"); + NV_ERROR(dev, "CURSOR_CTRL2 = 0x%08x\n", + nv_rd32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i))); + return -EBUSY; + } + + nv_wr32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), + NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_ON); + if (!nv_wait(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i), + NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS, + NV50_PDISPLAY_CURSOR_CURSOR_CTRL2_STATUS_ACTIVE)) { + NV_ERROR(dev, "timeout: " + "CURSOR_CTRL2_STATUS_ACTIVE(%d)\n", i); + NV_ERROR(dev, "CURSOR_CTRL2(%d) = 0x%08x\n", i, + nv_rd32(dev, NV50_PDISPLAY_CURSOR_CURSOR_CTRL2(i))); + return -EBUSY; + } + } + + nv_wr32(dev, NV50_PDISPLAY_OBJECTS, (evo->evo_obj->start >> 8) | 9); + + /* initialise fifo */ + nv_wr32(dev, NV50_PDISPLAY_CHANNEL_DMA_CB(0), + ((evo->pushbuf->start) >> 8) | + NV50_PDISPLAY_CHANNEL_DMA_CB_LOCATION_VRAM | + NV50_PDISPLAY_CHANNEL_DMA_CB_VALID); + nv_wr32(dev, NV50_PDISPLAY_CHANNEL_UNK2(0), 0x00010000); + nv_wr32(dev, NV50_PDISPLAY_CHANNEL_UNK3(0), 0x00000002); + if (!nv_wait(dev, 0x610200, 0x80000000, 0x00000000)) { + NV_ERROR(dev, "timeout: (0x610200 & 0x80000000) == 0\n"); + NV_ERROR(dev, "0x610200 = 0x%08x\n", nv_rd32(dev, 0x610200)); + return -EBUSY; + } + nv_wr32(dev, NV50_PDISPLAY_CHANNEL_STAT(0), + (nv_rd32(dev, NV50_PDISPLAY_CHANNEL_STAT(0)) & ~0x00000003) | + NV50_PDISPLAY_CHANNEL_STAT_DMA_ENABLED); + nv_wr32(dev, NV50_PDISPLAY_USER_PUT(0), 0); + nv_wr32(dev, NV50_PDISPLAY_CHANNEL_STAT(0), 0x01000003 | + NV50_PDISPLAY_CHANNEL_STAT_DMA_ENABLED); + nv_wr32(dev, 0x610300, nv_rd32(dev, 0x610300) & ~1); + + evo->dma.max = (4096/4) - 2; + evo->dma.put = 0; + evo->dma.cur = evo->dma.put; + evo->dma.free = evo->dma.max - evo->dma.cur; + + ret = RING_SPACE(evo, NOUVEAU_DMA_SKIPS); + if (ret) + return ret; + + for (i = 0; i < NOUVEAU_DMA_SKIPS; i++) + OUT_RING(evo, 0); + + ret = RING_SPACE(evo, 11); + if (ret) + return ret; + BEGIN_RING(evo, 0, NV50_EVO_UNK84, 2); + OUT_RING(evo, NV50_EVO_UNK84_NOTIFY_DISABLED); + OUT_RING(evo, NV50_EVO_DMA_NOTIFY_HANDLE_NONE); + BEGIN_RING(evo, 0, NV50_EVO_CRTC(0, FB_DMA), 1); + OUT_RING(evo, NV50_EVO_CRTC_FB_DMA_HANDLE_NONE); + BEGIN_RING(evo, 0, NV50_EVO_CRTC(0, UNK0800), 1); + OUT_RING(evo, 0); + BEGIN_RING(evo, 0, NV50_EVO_CRTC(0, DISPLAY_START), 1); + OUT_RING(evo, 0); + BEGIN_RING(evo, 0, NV50_EVO_CRTC(0, UNK082C), 1); + OUT_RING(evo, 0); + FIRE_RING(evo); + if (!nv_wait(dev, 0x640004, 0xffffffff, evo->dma.put << 2)) + NV_ERROR(dev, "evo pushbuf stalled\n"); + + /* enable clock change interrupts. */ + nv_wr32(dev, 0x610028, 0x00010001); + nv_wr32(dev, NV50_PDISPLAY_INTR_EN, (NV50_PDISPLAY_INTR_EN_CLK_UNK10 | + NV50_PDISPLAY_INTR_EN_CLK_UNK20 | + NV50_PDISPLAY_INTR_EN_CLK_UNK40)); + + /* enable hotplug interrupts */ + list_for_each_entry(connector, &dev->mode_config.connector_list, head) { + struct nouveau_connector *conn = nouveau_connector(connector); + + if (conn->dcb->gpio_tag == 0xff) + continue; + + pgpio->irq_enable(dev, conn->dcb->gpio_tag, true); + } + + return 0; +} + +static int nv50_display_disable(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct drm_crtc *drm_crtc; + int ret, i; + + NV_DEBUG_KMS(dev, "\n"); + + list_for_each_entry(drm_crtc, &dev->mode_config.crtc_list, head) { + struct nouveau_crtc *crtc = nouveau_crtc(drm_crtc); + + nv50_crtc_blank(crtc, true); + } + + ret = RING_SPACE(dev_priv->evo, 2); + if (ret == 0) { + BEGIN_RING(dev_priv->evo, 0, NV50_EVO_UPDATE, 1); + OUT_RING(dev_priv->evo, 0); + } + FIRE_RING(dev_priv->evo); + + /* Almost like ack'ing a vblank interrupt, maybe in the spirit of + * cleaning up? + */ + list_for_each_entry(drm_crtc, &dev->mode_config.crtc_list, head) { + struct nouveau_crtc *crtc = nouveau_crtc(drm_crtc); + uint32_t mask = NV50_PDISPLAY_INTR_1_VBLANK_CRTC_(crtc->index); + + if (!crtc->base.enabled) + continue; + + nv_wr32(dev, NV50_PDISPLAY_INTR_1, mask); + if (!nv_wait(dev, NV50_PDISPLAY_INTR_1, mask, mask)) { + NV_ERROR(dev, "timeout: (0x610024 & 0x%08x) == " + "0x%08x\n", mask, mask); + NV_ERROR(dev, "0x610024 = 0x%08x\n", + nv_rd32(dev, NV50_PDISPLAY_INTR_1)); + } + } + + nv_wr32(dev, NV50_PDISPLAY_CHANNEL_STAT(0), 0); + nv_wr32(dev, NV50_PDISPLAY_CTRL_STATE, 0); + if (!nv_wait(dev, NV50_PDISPLAY_CHANNEL_STAT(0), 0x1e0000, 0)) { + NV_ERROR(dev, "timeout: (0x610200 & 0x1e0000) == 0\n"); + NV_ERROR(dev, "0x610200 = 0x%08x\n", + nv_rd32(dev, NV50_PDISPLAY_CHANNEL_STAT(0))); + } + + for (i = 0; i < 3; i++) { + if (!nv_wait(dev, NV50_PDISPLAY_SOR_DPMS_STATE(i), + NV50_PDISPLAY_SOR_DPMS_STATE_WAIT, 0)) { + NV_ERROR(dev, "timeout: SOR_DPMS_STATE_WAIT(%d) == 0\n", i); + NV_ERROR(dev, "SOR_DPMS_STATE(%d) = 0x%08x\n", i, + nv_rd32(dev, NV50_PDISPLAY_SOR_DPMS_STATE(i))); + } + } + + /* disable interrupts. */ + nv_wr32(dev, NV50_PDISPLAY_INTR_EN, 0x00000000); + + /* disable hotplug interrupts */ + nv_wr32(dev, 0xe054, 0xffffffff); + nv_wr32(dev, 0xe050, 0x00000000); + if (dev_priv->chipset >= 0x90) { + nv_wr32(dev, 0xe074, 0xffffffff); + nv_wr32(dev, 0xe070, 0x00000000); + } + return 0; +} + +int nv50_display_create(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct dcb_table *dcb = &dev_priv->vbios.dcb; + struct drm_connector *connector, *ct; + int ret, i; + + NV_DEBUG_KMS(dev, "\n"); + + /* init basic kernel modesetting */ + drm_mode_config_init(dev); + + /* Initialise some optional connector properties. */ + drm_mode_create_scaling_mode_property(dev); + drm_mode_create_dithering_property(dev); + + dev->mode_config.min_width = 0; + dev->mode_config.min_height = 0; + + dev->mode_config.funcs = (void *)&nouveau_mode_config_funcs; + + dev->mode_config.max_width = 8192; + dev->mode_config.max_height = 8192; + + dev->mode_config.fb_base = dev_priv->fb_phys; + + /* Create EVO channel */ + ret = nv50_evo_channel_new(dev, &dev_priv->evo); + if (ret) { + NV_ERROR(dev, "Error creating EVO channel: %d\n", ret); + return ret; + } + + /* Create CRTC objects */ + for (i = 0; i < 2; i++) + nv50_crtc_create(dev, i); + + /* We setup the encoders from the BIOS table */ + for (i = 0 ; i < dcb->entries; i++) { + struct dcb_entry *entry = &dcb->entry[i]; + + if (entry->location != DCB_LOC_ON_CHIP) { + NV_WARN(dev, "Off-chip encoder %d/%d unsupported\n", + entry->type, ffs(entry->or) - 1); + continue; + } + + connector = nouveau_connector_create(dev, entry->connector); + if (IS_ERR(connector)) + continue; + + switch (entry->type) { + case OUTPUT_TMDS: + case OUTPUT_LVDS: + case OUTPUT_DP: + nv50_sor_create(connector, entry); + break; + case OUTPUT_ANALOG: + nv50_dac_create(connector, entry); + break; + default: + NV_WARN(dev, "DCB encoder %d unknown\n", entry->type); + continue; + } + } + + list_for_each_entry_safe(connector, ct, + &dev->mode_config.connector_list, head) { + if (!connector->encoder_ids[0]) { + NV_WARN(dev, "%s has no encoders, removing\n", + drm_get_connector_name(connector)); + connector->funcs->destroy(connector); + } + } + + ret = nv50_display_init(dev); + if (ret) { + nv50_display_destroy(dev); + return ret; + } + + return 0; +} + +void +nv50_display_destroy(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + NV_DEBUG_KMS(dev, "\n"); + + drm_mode_config_cleanup(dev); + + nv50_display_disable(dev); + nv50_evo_channel_del(&dev_priv->evo); +} + +static u16 +nv50_display_script_select(struct drm_device *dev, struct dcb_entry *dcb, + u32 mc, int pxclk) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_connector *nv_connector = NULL; + struct drm_encoder *encoder; + struct nvbios *bios = &dev_priv->vbios; + u32 script = 0, or; + + list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + + if (nv_encoder->dcb != dcb) + continue; + + nv_connector = nouveau_encoder_connector_get(nv_encoder); + break; + } + + or = ffs(dcb->or) - 1; + switch (dcb->type) { + case OUTPUT_LVDS: + script = (mc >> 8) & 0xf; + if (bios->fp_no_ddc) { + if (bios->fp.dual_link) + script |= 0x0100; + if (bios->fp.if_is_24bit) + script |= 0x0200; + } else { + if (pxclk >= bios->fp.duallink_transition_clk) { + script |= 0x0100; + if (bios->fp.strapless_is_24bit & 2) + script |= 0x0200; + } else + if (bios->fp.strapless_is_24bit & 1) + script |= 0x0200; + + if (nv_connector && nv_connector->edid && + (nv_connector->edid->revision >= 4) && + (nv_connector->edid->input & 0x70) >= 0x20) + script |= 0x0200; + } + + if (nouveau_uscript_lvds >= 0) { + NV_INFO(dev, "override script 0x%04x with 0x%04x " + "for output LVDS-%d\n", script, + nouveau_uscript_lvds, or); + script = nouveau_uscript_lvds; + } + break; + case OUTPUT_TMDS: + script = (mc >> 8) & 0xf; + if (pxclk >= 165000) + script |= 0x0100; + + if (nouveau_uscript_tmds >= 0) { + NV_INFO(dev, "override script 0x%04x with 0x%04x " + "for output TMDS-%d\n", script, + nouveau_uscript_tmds, or); + script = nouveau_uscript_tmds; + } + break; + case OUTPUT_DP: + script = (mc >> 8) & 0xf; + break; + case OUTPUT_ANALOG: + script = 0xff; + break; + default: + NV_ERROR(dev, "modeset on unsupported output type!\n"); + break; + } + + return script; +} + +static void +nv50_display_vblank_crtc_handler(struct drm_device *dev, int crtc) +{ +#if 0 + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *chan; + struct list_head *entry, *tmp; + + list_for_each_safe(entry, tmp, &dev_priv->vbl_waiting) { + chan = list_entry(entry, struct nouveau_channel, nvsw.vbl_wait); + + nouveau_bo_wr32(chan->notifier_bo, chan->nvsw.vblsem_offset, + chan->nvsw.vblsem_rval); + list_del(&chan->nvsw.vbl_wait); + } +#endif +} + +static void +nv50_display_vblank_handler(struct drm_device *dev, uint32_t intr) +{ + intr &= NV50_PDISPLAY_INTR_1_VBLANK_CRTC; + + if (intr & NV50_PDISPLAY_INTR_1_VBLANK_CRTC_0) + nv50_display_vblank_crtc_handler(dev, 0); + + if (intr & NV50_PDISPLAY_INTR_1_VBLANK_CRTC_1) + nv50_display_vblank_crtc_handler(dev, 1); + + nv_wr32(dev, NV50_PDISPLAY_INTR_EN, nv_rd32(dev, + NV50_PDISPLAY_INTR_EN) & ~intr); + nv_wr32(dev, NV50_PDISPLAY_INTR_1, intr); +} + +static void +nv50_display_unk10_handler(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + u32 unk30 = nv_rd32(dev, 0x610030), mc; + int i, crtc, or, type = OUTPUT_ANY; + + NV_DEBUG_KMS(dev, "0x610030: 0x%08x\n", unk30); + dev_priv->evo_irq.dcb = NULL; + + nv_wr32(dev, 0x619494, nv_rd32(dev, 0x619494) & ~8); + + /* Determine which CRTC we're dealing with, only 1 ever will be + * signalled at the same time with the current nouveau code. + */ + crtc = ffs((unk30 & 0x00000060) >> 5) - 1; + if (crtc < 0) + goto ack; + + /* Nothing needs to be done for the encoder */ + crtc = ffs((unk30 & 0x00000180) >> 7) - 1; + if (crtc < 0) + goto ack; + + /* Find which encoder was connected to the CRTC */ + for (i = 0; type == OUTPUT_ANY && i < 3; i++) { + mc = nv_rd32(dev, NV50_PDISPLAY_DAC_MODE_CTRL_C(i)); + NV_DEBUG_KMS(dev, "DAC-%d mc: 0x%08x\n", i, mc); + if (!(mc & (1 << crtc))) + continue; + + switch ((mc & 0x00000f00) >> 8) { + case 0: type = OUTPUT_ANALOG; break; + case 1: type = OUTPUT_TV; break; + default: + NV_ERROR(dev, "invalid mc, DAC-%d: 0x%08x\n", i, mc); + goto ack; + } + + or = i; + } + + for (i = 0; type == OUTPUT_ANY && i < nv50_sor_nr(dev); i++) { + if (dev_priv->chipset < 0x90 || + dev_priv->chipset == 0x92 || + dev_priv->chipset == 0xa0) + mc = nv_rd32(dev, NV50_PDISPLAY_SOR_MODE_CTRL_C(i)); + else + mc = nv_rd32(dev, NV90_PDISPLAY_SOR_MODE_CTRL_C(i)); + + NV_DEBUG_KMS(dev, "SOR-%d mc: 0x%08x\n", i, mc); + if (!(mc & (1 << crtc))) + continue; + + switch ((mc & 0x00000f00) >> 8) { + case 0: type = OUTPUT_LVDS; break; + case 1: type = OUTPUT_TMDS; break; + case 2: type = OUTPUT_TMDS; break; + case 5: type = OUTPUT_TMDS; break; + case 8: type = OUTPUT_DP; break; + case 9: type = OUTPUT_DP; break; + default: + NV_ERROR(dev, "invalid mc, SOR-%d: 0x%08x\n", i, mc); + goto ack; + } + + or = i; + } + + /* There was no encoder to disable */ + if (type == OUTPUT_ANY) + goto ack; + + /* Disable the encoder */ + for (i = 0; i < dev_priv->vbios.dcb.entries; i++) { + struct dcb_entry *dcb = &dev_priv->vbios.dcb.entry[i]; + + if (dcb->type == type && (dcb->or & (1 << or))) { + nouveau_bios_run_display_table(dev, dcb, 0, -1); + dev_priv->evo_irq.dcb = dcb; + goto ack; + } + } + + NV_ERROR(dev, "no dcb for %d %d 0x%08x\n", or, type, mc); +ack: + nv_wr32(dev, NV50_PDISPLAY_INTR_1, NV50_PDISPLAY_INTR_1_CLK_UNK10); + nv_wr32(dev, 0x610030, 0x80000000); +} + +static void +nv50_display_unk20_dp_hack(struct drm_device *dev, struct dcb_entry *dcb) +{ + int or = ffs(dcb->or) - 1, link = !(dcb->dpconf.sor.link & 1); + struct drm_encoder *encoder; + uint32_t tmp, unk0 = 0, unk1 = 0; + + if (dcb->type != OUTPUT_DP) + return; + + list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + + if (nv_encoder->dcb == dcb) { + unk0 = nv_encoder->dp.unk0; + unk1 = nv_encoder->dp.unk1; + break; + } + } + + if (unk0 || unk1) { + tmp = nv_rd32(dev, NV50_SOR_DP_CTRL(or, link)); + tmp &= 0xfffffe03; + nv_wr32(dev, NV50_SOR_DP_CTRL(or, link), tmp | unk0); + + tmp = nv_rd32(dev, NV50_SOR_DP_UNK128(or, link)); + tmp &= 0xfef080c0; + nv_wr32(dev, NV50_SOR_DP_UNK128(or, link), tmp | unk1); + } +} + +static void +nv50_display_unk20_handler(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + u32 tmp, pclk, script, mc = 0; + u32 unk30 = nv_rd32(dev, 0x610030); + struct dcb_entry *dcb; + int i, crtc, or, type = OUTPUT_ANY; + + NV_DEBUG_KMS(dev, "0x610030: 0x%08x\n", unk30); + dcb = dev_priv->evo_irq.dcb; + if (dcb) { + nouveau_bios_run_display_table(dev, dcb, 0, -2); + dev_priv->evo_irq.dcb = NULL; + } + + /* CRTC clock change requested? */ + crtc = ffs((unk30 & 0x00000600) >> 9) - 1; + if (crtc >= 0) { + pclk = nv_rd32(dev, NV50_PDISPLAY_CRTC_P(crtc, CLOCK)); + pclk &= 0x003fffff; + + nv50_crtc_set_clock(dev, crtc, pclk); + + tmp = nv_rd32(dev, NV50_PDISPLAY_CRTC_CLK_CTRL2(crtc)); + tmp &= ~0x000000f; + nv_wr32(dev, NV50_PDISPLAY_CRTC_CLK_CTRL2(crtc), tmp); + } + + /* Nothing needs to be done for the encoder */ + crtc = ffs((unk30 & 0x00000180) >> 7) - 1; + if (crtc < 0) + goto ack; + pclk = nv_rd32(dev, NV50_PDISPLAY_CRTC_P(crtc, CLOCK)) & 0x003fffff; + + /* Find which encoder is connected to the CRTC */ + for (i = 0; type == OUTPUT_ANY && i < 3; i++) { + mc = nv_rd32(dev, NV50_PDISPLAY_DAC_MODE_CTRL_P(i)); + NV_DEBUG_KMS(dev, "DAC-%d mc: 0x%08x\n", i, mc); + if (!(mc & (1 << crtc))) + continue; + + switch ((mc & 0x00000f00) >> 8) { + case 0: type = OUTPUT_ANALOG; break; + case 1: type = OUTPUT_TV; break; + default: + NV_ERROR(dev, "invalid mc, DAC-%d: 0x%08x\n", i, mc); + goto ack; + } + + or = i; + } + + for (i = 0; type == OUTPUT_ANY && i < nv50_sor_nr(dev); i++) { + if (dev_priv->chipset < 0x90 || + dev_priv->chipset == 0x92 || + dev_priv->chipset == 0xa0) + mc = nv_rd32(dev, NV50_PDISPLAY_SOR_MODE_CTRL_P(i)); + else + mc = nv_rd32(dev, NV90_PDISPLAY_SOR_MODE_CTRL_P(i)); + + NV_DEBUG_KMS(dev, "SOR-%d mc: 0x%08x\n", i, mc); + if (!(mc & (1 << crtc))) + continue; + + switch ((mc & 0x00000f00) >> 8) { + case 0: type = OUTPUT_LVDS; break; + case 1: type = OUTPUT_TMDS; break; + case 2: type = OUTPUT_TMDS; break; + case 5: type = OUTPUT_TMDS; break; + case 8: type = OUTPUT_DP; break; + case 9: type = OUTPUT_DP; break; + default: + NV_ERROR(dev, "invalid mc, SOR-%d: 0x%08x\n", i, mc); + goto ack; + } + + or = i; + } + + if (type == OUTPUT_ANY) + goto ack; + + /* Enable the encoder */ + for (i = 0; i < dev_priv->vbios.dcb.entries; i++) { + dcb = &dev_priv->vbios.dcb.entry[i]; + if (dcb->type == type && (dcb->or & (1 << or))) + break; + } + + if (i == dev_priv->vbios.dcb.entries) { + NV_ERROR(dev, "no dcb for %d %d 0x%08x\n", or, type, mc); + goto ack; + } + + script = nv50_display_script_select(dev, dcb, mc, pclk); + nouveau_bios_run_display_table(dev, dcb, script, pclk); + + nv50_display_unk20_dp_hack(dev, dcb); + + if (dcb->type != OUTPUT_ANALOG) { + tmp = nv_rd32(dev, NV50_PDISPLAY_SOR_CLK_CTRL2(or)); + tmp &= ~0x00000f0f; + if (script & 0x0100) + tmp |= 0x00000101; + nv_wr32(dev, NV50_PDISPLAY_SOR_CLK_CTRL2(or), tmp); + } else { + nv_wr32(dev, NV50_PDISPLAY_DAC_CLK_CTRL2(or), 0); + } + + dev_priv->evo_irq.dcb = dcb; + dev_priv->evo_irq.pclk = pclk; + dev_priv->evo_irq.script = script; + +ack: + nv_wr32(dev, NV50_PDISPLAY_INTR_1, NV50_PDISPLAY_INTR_1_CLK_UNK20); + nv_wr32(dev, 0x610030, 0x80000000); +} + +/* If programming a TMDS output on a SOR that can also be configured for + * DisplayPort, make sure NV50_SOR_DP_CTRL_ENABLE is forced off. + * + * It looks like the VBIOS TMDS scripts make an attempt at this, however, + * the VBIOS scripts on at least one board I have only switch it off on + * link 0, causing a blank display if the output has previously been + * programmed for DisplayPort. + */ +static void +nv50_display_unk40_dp_set_tmds(struct drm_device *dev, struct dcb_entry *dcb) +{ + int or = ffs(dcb->or) - 1, link = !(dcb->dpconf.sor.link & 1); + struct drm_encoder *encoder; + u32 tmp; + + if (dcb->type != OUTPUT_TMDS) + return; + + list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + + if (nv_encoder->dcb->type == OUTPUT_DP && + nv_encoder->dcb->or & (1 << or)) { + tmp = nv_rd32(dev, NV50_SOR_DP_CTRL(or, link)); + tmp &= ~NV50_SOR_DP_CTRL_ENABLED; + nv_wr32(dev, NV50_SOR_DP_CTRL(or, link), tmp); + break; + } + } +} + +static void +nv50_display_unk40_handler(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct dcb_entry *dcb = dev_priv->evo_irq.dcb; + u16 script = dev_priv->evo_irq.script; + u32 unk30 = nv_rd32(dev, 0x610030), pclk = dev_priv->evo_irq.pclk; + + NV_DEBUG_KMS(dev, "0x610030: 0x%08x\n", unk30); + dev_priv->evo_irq.dcb = NULL; + if (!dcb) + goto ack; + + nouveau_bios_run_display_table(dev, dcb, script, -pclk); + nv50_display_unk40_dp_set_tmds(dev, dcb); + +ack: + nv_wr32(dev, NV50_PDISPLAY_INTR_1, NV50_PDISPLAY_INTR_1_CLK_UNK40); + nv_wr32(dev, 0x610030, 0x80000000); + nv_wr32(dev, 0x619494, nv_rd32(dev, 0x619494) | 8); +} + +void +nv50_display_irq_handler_bh(struct work_struct *work) +{ + struct drm_nouveau_private *dev_priv = + container_of(work, struct drm_nouveau_private, irq_work); + struct drm_device *dev = dev_priv->dev; + + for (;;) { + uint32_t intr0 = nv_rd32(dev, NV50_PDISPLAY_INTR_0); + uint32_t intr1 = nv_rd32(dev, NV50_PDISPLAY_INTR_1); + + NV_DEBUG_KMS(dev, "PDISPLAY_INTR_BH 0x%08x 0x%08x\n", intr0, intr1); + + if (intr1 & NV50_PDISPLAY_INTR_1_CLK_UNK10) + nv50_display_unk10_handler(dev); + else + if (intr1 & NV50_PDISPLAY_INTR_1_CLK_UNK20) + nv50_display_unk20_handler(dev); + else + if (intr1 & NV50_PDISPLAY_INTR_1_CLK_UNK40) + nv50_display_unk40_handler(dev); + else + break; + } + + nv_wr32(dev, NV03_PMC_INTR_EN_0, 1); +} + +static void +nv50_display_error_handler(struct drm_device *dev) +{ + uint32_t addr, data; + + nv_wr32(dev, NV50_PDISPLAY_INTR_0, 0x00010000); + addr = nv_rd32(dev, NV50_PDISPLAY_TRAPPED_ADDR); + data = nv_rd32(dev, NV50_PDISPLAY_TRAPPED_DATA); + + NV_ERROR(dev, "EvoCh %d Mthd 0x%04x Data 0x%08x (0x%04x 0x%02x)\n", + 0, addr & 0xffc, data, addr >> 16, (addr >> 12) & 0xf); + + nv_wr32(dev, NV50_PDISPLAY_TRAPPED_ADDR, 0x90000000); +} + +void +nv50_display_irq_hotplug_bh(struct work_struct *work) +{ + struct drm_nouveau_private *dev_priv = + container_of(work, struct drm_nouveau_private, hpd_work); + struct drm_device *dev = dev_priv->dev; + struct drm_connector *connector; + const uint32_t gpio_reg[4] = { 0xe104, 0xe108, 0xe280, 0xe284 }; + uint32_t unplug_mask, plug_mask, change_mask; + uint32_t hpd0, hpd1 = 0; + + hpd0 = nv_rd32(dev, 0xe054) & nv_rd32(dev, 0xe050); + if (dev_priv->chipset >= 0x90) + hpd1 = nv_rd32(dev, 0xe074) & nv_rd32(dev, 0xe070); + + plug_mask = (hpd0 & 0x0000ffff) | (hpd1 << 16); + unplug_mask = (hpd0 >> 16) | (hpd1 & 0xffff0000); + change_mask = plug_mask | unplug_mask; + + list_for_each_entry(connector, &dev->mode_config.connector_list, head) { + struct drm_encoder_helper_funcs *helper; + struct nouveau_connector *nv_connector = + nouveau_connector(connector); + struct nouveau_encoder *nv_encoder; + struct dcb_gpio_entry *gpio; + uint32_t reg; + bool plugged; + + if (!nv_connector->dcb) + continue; + + gpio = nouveau_bios_gpio_entry(dev, nv_connector->dcb->gpio_tag); + if (!gpio || !(change_mask & (1 << gpio->line))) + continue; + + reg = nv_rd32(dev, gpio_reg[gpio->line >> 3]); + plugged = !!(reg & (4 << ((gpio->line & 7) << 2))); + NV_INFO(dev, "%splugged %s\n", plugged ? "" : "un", + drm_get_connector_name(connector)) ; + + if (!connector->encoder || !connector->encoder->crtc || + !connector->encoder->crtc->enabled) + continue; + nv_encoder = nouveau_encoder(connector->encoder); + helper = connector->encoder->helper_private; + + if (nv_encoder->dcb->type != OUTPUT_DP) + continue; + + if (plugged) + helper->dpms(connector->encoder, DRM_MODE_DPMS_ON); + else + helper->dpms(connector->encoder, DRM_MODE_DPMS_OFF); + } + + nv_wr32(dev, 0xe054, nv_rd32(dev, 0xe054)); + if (dev_priv->chipset >= 0x90) + nv_wr32(dev, 0xe074, nv_rd32(dev, 0xe074)); + + drm_helper_hpd_irq_event(dev); +} + +void +nv50_display_irq_handler(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t delayed = 0; + + if (nv_rd32(dev, NV50_PMC_INTR_0) & NV50_PMC_INTR_0_HOTPLUG) { + if (!work_pending(&dev_priv->hpd_work)) + queue_work(dev_priv->wq, &dev_priv->hpd_work); + } + + while (nv_rd32(dev, NV50_PMC_INTR_0) & NV50_PMC_INTR_0_DISPLAY) { + uint32_t intr0 = nv_rd32(dev, NV50_PDISPLAY_INTR_0); + uint32_t intr1 = nv_rd32(dev, NV50_PDISPLAY_INTR_1); + uint32_t clock; + + NV_DEBUG_KMS(dev, "PDISPLAY_INTR 0x%08x 0x%08x\n", intr0, intr1); + + if (!intr0 && !(intr1 & ~delayed)) + break; + + if (intr0 & 0x00010000) { + nv50_display_error_handler(dev); + intr0 &= ~0x00010000; + } + + if (intr1 & NV50_PDISPLAY_INTR_1_VBLANK_CRTC) { + nv50_display_vblank_handler(dev, intr1); + intr1 &= ~NV50_PDISPLAY_INTR_1_VBLANK_CRTC; + } + + clock = (intr1 & (NV50_PDISPLAY_INTR_1_CLK_UNK10 | + NV50_PDISPLAY_INTR_1_CLK_UNK20 | + NV50_PDISPLAY_INTR_1_CLK_UNK40)); + if (clock) { + nv_wr32(dev, NV03_PMC_INTR_EN_0, 0); + if (!work_pending(&dev_priv->irq_work)) + queue_work(dev_priv->wq, &dev_priv->irq_work); + delayed |= clock; + intr1 &= ~clock; + } + + if (intr0) { + NV_ERROR(dev, "unknown PDISPLAY_INTR_0: 0x%08x\n", intr0); + nv_wr32(dev, NV50_PDISPLAY_INTR_0, intr0); + } + + if (intr1) { + NV_ERROR(dev, + "unknown PDISPLAY_INTR_1: 0x%08x\n", intr1); + nv_wr32(dev, NV50_PDISPLAY_INTR_1, intr1); + } + } +} + diff --git a/driver/pscnv/nv50_display.h b/driver/pscnv/nv50_display.h new file mode 100644 index 00000000..c551f0b8 --- /dev/null +++ b/driver/pscnv/nv50_display.h @@ -0,0 +1,49 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#ifndef __NV50_DISPLAY_H__ +#define __NV50_DISPLAY_H__ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "nouveau_dma.h" +#include "nouveau_reg.h" +#include "nouveau_crtc.h" +#include "nv50_evo.h" + +void nv50_display_irq_handler(struct drm_device *dev); +void nv50_display_irq_handler_bh(struct work_struct *work); +void nv50_display_irq_hotplug_bh(struct work_struct *work); +int nv50_display_early_init(struct drm_device *dev); +void nv50_display_late_takedown(struct drm_device *dev); +int nv50_display_create(struct drm_device *dev); +int nv50_display_init(struct drm_device *dev); +void nv50_display_destroy(struct drm_device *dev); +int nv50_crtc_blank(struct nouveau_crtc *, bool blank); +int nv50_crtc_set_clock(struct drm_device *, int head, int pclk); + +#endif /* __NV50_DISPLAY_H__ */ diff --git a/driver/pscnv/nv50_evo.h b/driver/pscnv/nv50_evo.h new file mode 100644 index 00000000..aae13343 --- /dev/null +++ b/driver/pscnv/nv50_evo.h @@ -0,0 +1,113 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#define NV50_EVO_UPDATE 0x00000080 +#define NV50_EVO_UNK84 0x00000084 +#define NV50_EVO_UNK84_NOTIFY 0x40000000 +#define NV50_EVO_UNK84_NOTIFY_DISABLED 0x00000000 +#define NV50_EVO_UNK84_NOTIFY_ENABLED 0x40000000 +#define NV50_EVO_DMA_NOTIFY 0x00000088 +#define NV50_EVO_DMA_NOTIFY_HANDLE 0xffffffff +#define NV50_EVO_DMA_NOTIFY_HANDLE_NONE 0x00000000 +#define NV50_EVO_UNK8C 0x0000008C + +#define NV50_EVO_DAC(n, r) ((n) * 0x80 + NV50_EVO_DAC_##r) +#define NV50_EVO_DAC_MODE_CTRL 0x00000400 +#define NV50_EVO_DAC_MODE_CTRL_CRTC0 0x00000001 +#define NV50_EVO_DAC_MODE_CTRL_CRTC1 0x00000002 +#define NV50_EVO_DAC_MODE_CTRL2 0x00000404 +#define NV50_EVO_DAC_MODE_CTRL2_NHSYNC 0x00000001 +#define NV50_EVO_DAC_MODE_CTRL2_NVSYNC 0x00000002 + +#define NV50_EVO_SOR(n, r) ((n) * 0x40 + NV50_EVO_SOR_##r) +#define NV50_EVO_SOR_MODE_CTRL 0x00000600 +#define NV50_EVO_SOR_MODE_CTRL_CRTC0 0x00000001 +#define NV50_EVO_SOR_MODE_CTRL_CRTC1 0x00000002 +#define NV50_EVO_SOR_MODE_CTRL_TMDS 0x00000100 +#define NV50_EVO_SOR_MODE_CTRL_TMDS_DUAL_LINK 0x00000400 +#define NV50_EVO_SOR_MODE_CTRL_NHSYNC 0x00001000 +#define NV50_EVO_SOR_MODE_CTRL_NVSYNC 0x00002000 + +#define NV50_EVO_CRTC(n, r) ((n) * 0x400 + NV50_EVO_CRTC_##r) +#define NV84_EVO_CRTC(n, r) ((n) * 0x400 + NV84_EVO_CRTC_##r) +#define NV50_EVO_CRTC_UNK0800 0x00000800 +#define NV50_EVO_CRTC_CLOCK 0x00000804 +#define NV50_EVO_CRTC_INTERLACE 0x00000808 +#define NV50_EVO_CRTC_DISPLAY_START 0x00000810 +#define NV50_EVO_CRTC_DISPLAY_TOTAL 0x00000814 +#define NV50_EVO_CRTC_SYNC_DURATION 0x00000818 +#define NV50_EVO_CRTC_SYNC_START_TO_BLANK_END 0x0000081c +#define NV50_EVO_CRTC_UNK0820 0x00000820 +#define NV50_EVO_CRTC_UNK0824 0x00000824 +#define NV50_EVO_CRTC_UNK082C 0x0000082c +#define NV50_EVO_CRTC_CLUT_MODE 0x00000840 +/* You can't have a palette in 8 bit mode (=OFF) */ +#define NV50_EVO_CRTC_CLUT_MODE_BLANK 0x00000000 +#define NV50_EVO_CRTC_CLUT_MODE_OFF 0x80000000 +#define NV50_EVO_CRTC_CLUT_MODE_ON 0xC0000000 +#define NV50_EVO_CRTC_CLUT_OFFSET 0x00000844 +#define NV84_EVO_CRTC_CLUT_DMA 0x0000085C +#define NV84_EVO_CRTC_CLUT_DMA_HANDLE 0xffffffff +#define NV84_EVO_CRTC_CLUT_DMA_HANDLE_NONE 0x00000000 +#define NV50_EVO_CRTC_FB_OFFSET 0x00000860 +#define NV50_EVO_CRTC_FB_SIZE 0x00000868 +#define NV50_EVO_CRTC_FB_CONFIG 0x0000086c +#define NV50_EVO_CRTC_FB_CONFIG_MODE 0x00100000 +#define NV50_EVO_CRTC_FB_CONFIG_MODE_TILE 0x00000000 +#define NV50_EVO_CRTC_FB_CONFIG_MODE_PITCH 0x00100000 +#define NV50_EVO_CRTC_FB_DEPTH 0x00000870 +#define NV50_EVO_CRTC_FB_DEPTH_8 0x00001e00 +#define NV50_EVO_CRTC_FB_DEPTH_15 0x0000e900 +#define NV50_EVO_CRTC_FB_DEPTH_16 0x0000e800 +#define NV50_EVO_CRTC_FB_DEPTH_24 0x0000cf00 +#define NV50_EVO_CRTC_FB_DEPTH_30 0x0000d100 +#define NV50_EVO_CRTC_FB_DMA 0x00000874 +#define NV50_EVO_CRTC_FB_DMA_HANDLE 0xffffffff +#define NV50_EVO_CRTC_FB_DMA_HANDLE_NONE 0x00000000 +#define NV50_EVO_CRTC_CURSOR_CTRL 0x00000880 +#define NV50_EVO_CRTC_CURSOR_CTRL_HIDE 0x05000000 +#define NV50_EVO_CRTC_CURSOR_CTRL_SHOW 0x85000000 +#define NV50_EVO_CRTC_CURSOR_OFFSET 0x00000884 +#define NV84_EVO_CRTC_CURSOR_DMA 0x0000089c +#define NV84_EVO_CRTC_CURSOR_DMA_HANDLE 0xffffffff +#define NV84_EVO_CRTC_CURSOR_DMA_HANDLE_NONE 0x00000000 +#define NV50_EVO_CRTC_DITHER_CTRL 0x000008a0 +#define NV50_EVO_CRTC_DITHER_CTRL_OFF 0x00000000 +#define NV50_EVO_CRTC_DITHER_CTRL_ON 0x00000011 +#define NV50_EVO_CRTC_SCALE_CTRL 0x000008a4 +#define NV50_EVO_CRTC_SCALE_CTRL_INACTIVE 0x00000000 +#define NV50_EVO_CRTC_SCALE_CTRL_ACTIVE 0x00000009 +#define NV50_EVO_CRTC_COLOR_CTRL 0x000008a8 +#define NV50_EVO_CRTC_COLOR_CTRL_COLOR 0x00040000 +#define NV50_EVO_CRTC_FB_POS 0x000008c0 +#define NV50_EVO_CRTC_REAL_RES 0x000008c8 +#define NV50_EVO_CRTC_SCALE_CENTER_OFFSET 0x000008d4 +#define NV50_EVO_CRTC_SCALE_CENTER_OFFSET_VAL(x, y) \ + ((((unsigned)y << 16) & 0xFFFF0000) | (((unsigned)x) & 0x0000FFFF)) +/* Both of these are needed, otherwise nothing happens. */ +#define NV50_EVO_CRTC_SCALE_RES1 0x000008d8 +#define NV50_EVO_CRTC_SCALE_RES2 0x000008dc + diff --git a/driver/pscnv/nv50_fifo.c b/driver/pscnv/nv50_fifo.c new file mode 100644 index 00000000..9b19dcb7 --- /dev/null +++ b/driver/pscnv/nv50_fifo.c @@ -0,0 +1,460 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drm.h" +#include "drmP.h" +#include "nouveau_drv.h" +#include "pscnv_chan.h" +#include "pscnv_fifo.h" +#include "nv50_vm.h" + +struct nv50_fifo_engine { + struct pscnv_fifo_engine base; + spinlock_t lock; + struct pscnv_bo *playlist[2]; + int cur_playlist; +}; + +#define nv50_fifo(x) container_of(x, struct nv50_fifo_engine, base) + +void nv50_fifo_takedown(struct drm_device *dev); +void nv50_fifo_irq_handler(struct drm_device *dev, int irq); +int nv50_fifo_chan_init_dma (struct pscnv_chan *ch, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t pb_start); +int nv50_fifo_chan_init_ib (struct pscnv_chan *ch, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t ib_start, uint32_t ib_order); +void nv50_fifo_chan_kill(struct pscnv_chan *ch); + +int nv50_fifo_init(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + int i; + struct nv50_fifo_engine *res = kzalloc(sizeof *res, GFP_KERNEL); + + if (!res) { + NV_ERROR(dev, "PFIFO: Couldn't allocate engine!\n"); + return -ENOMEM; + } + + res->base.takedown = nv50_fifo_takedown; + res->base.chan_kill = nv50_fifo_chan_kill; + res->base.chan_init_dma = nv50_fifo_chan_init_dma; + res->base.chan_init_ib = nv50_fifo_chan_init_ib; + spin_lock_init(&res->lock); + + res->playlist[0] = pscnv_mem_alloc(dev, 0x1000, PSCNV_GEM_CONTIG, 0, 0x91a71157); + res->playlist[1] = pscnv_mem_alloc(dev, 0x1000, PSCNV_GEM_CONTIG, 0, 0x91a71157); + if (!res->playlist[0] || !res->playlist[1]) { + NV_ERROR(dev, "PFIFO: Couldn't allocate playlists!\n"); + if (res->playlist[0]) + pscnv_mem_free(res->playlist[0]); + if (res->playlist[1]) + pscnv_mem_free(res->playlist[1]); + kfree(res); + return -ENOMEM; + } + dev_priv->vm->map_kernel(res->playlist[0]); + dev_priv->vm->map_kernel(res->playlist[1]); + res->cur_playlist = 0; + + /* reset everything */ + nv_wr32(dev, 0x200, 0xfffffeff); + nv_wr32(dev, 0x200, 0xffffffff); + + /* clear channel table */ + for (i = 0; i < 128; i++) + nv_wr32(dev, 0x2600 + i * 4, 0); + + /* reset interrupts */ + nv_wr32(dev, 0x2100, -1); + + /* put PFIFO onto unused channel 0. */ + nv_wr32(dev, 0x3204, 0); + + /* clear GET, PUT */ + nv_wr32(dev, 0x3210, 0); + nv_wr32(dev, 0x3270, 0); + + /* enable everything. */ + nv_wr32(dev, 0x3250, 1); + nv_wr32(dev, 0x3220, 1); + nv_wr32(dev, 0x3200, 1); + nv_wr32(dev, 0x2500, 1); + + dev_priv->fifo = &res->base; + + /* enable interrupts */ + nouveau_irq_register(dev, 8, nv50_fifo_irq_handler); + nv_wr32(dev, 0x2140, -1); + return 0; +} + +void nv50_fifo_takedown(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + int i; + struct nv50_fifo_engine *fifo = nv50_fifo(dev_priv->fifo); + nv_wr32(dev, 0x2140, 0); + nouveau_irq_unregister(dev, 8); + for (i = 0; i < 128; i++) + nv_wr32(dev, 0x2600 + i * 4, 0); + nv_wr32(dev, 0x32ec, 0); + nv_wr32(dev, 0x2500, 0x101); + pscnv_mem_free(fifo->playlist[0]); + pscnv_mem_free(fifo->playlist[1]); + kfree(fifo); + dev_priv->fifo = 0; +} + +void nv50_fifo_playlist_update (struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv50_fifo_engine *fifo = nv50_fifo(dev_priv->fifo); + int i, pos; + struct pscnv_bo *vo; + fifo->cur_playlist ^= 1; + vo = fifo->playlist[fifo->cur_playlist]; + for (i = 0, pos = 0; i < 128; i++) { + if (nv_rd32(dev, 0x2600 + i * 4) & 0x80000000) { + nv_wv32(vo, pos, i); + pos += 4; + } + } + dev_priv->vm->bar_flush(dev); + /* XXX: is this correct? is this non-racy? */ + nv_wr32(dev, 0x32f4, vo->start >> 12); + nv_wr32(dev, 0x32ec, pos / 4); + nv_wr32(dev, 0x2500, 0x101); +} + +void nv50_fifo_chan_kill(struct pscnv_chan *ch) { + struct drm_device *dev = ch->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv50_fifo_engine *fifo = nv50_fifo(dev_priv->fifo); + uint64_t start; + unsigned long flags; + spin_lock_irqsave(&fifo->lock, flags); + nv_wr32(dev, 0x2600 + ch->cid * 4, nv_rd32(dev, 0x2600 + ch->cid * 4) & 0x3fffffff); + nv50_fifo_playlist_update(dev); + start = nv04_timer_read(dev); + nv_wr32(dev, 0x2500, 0); + if ((nv_rd32(dev, 0x3204) & 0x7f) == ch->cid) { + NV_INFO(dev, "Kicking channel %d off PFIFO.\n", ch->cid); + nv_wr32(dev, 0x204c, 0x20000); + } + nv_wr32(dev, 0x2500, 1); + + while ((nv_rd32(dev, 0x3204) & 0x7f) == ch->cid) { + uint32_t intr = nv_rd32(dev, 0x2100); + if (intr & 0x40011001 && (nv_rd32(dev, 0x3204) & 0x7f) == ch->cid) { + nv_wr32(dev, 0x2100, 0x40011001); + nv_wr32(dev, 0x3220, 1); + nv_wr32(dev, 0x3250, 1); + } + if (nv04_timer_read(dev) - start >= 2000000000) { + NV_ERROR(dev, "PFIFO kickoff wait fail!\n"); + break; + } + } + nv_wr32(dev, 0x2600 + ch->cid * 4, 0); + spin_unlock_irqrestore(&fifo->lock, flags); +} + +int nv50_fifo_chan_init_dma (struct pscnv_chan *ch, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t pb_start) { + struct drm_device *dev = ch->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv50_fifo_engine *fifo = nv50_fifo(dev_priv->fifo); + unsigned long irqflags; + uint32_t pb_inst; + + /* XXX: verify that we get a DMA object. */ + pb_inst = pscnv_ramht_find(&ch->ramht, pb_handle); + if (!pb_inst || pb_inst & 0xffff0000) { + return -ENOENT; + } + + spin_lock_irqsave(&fifo->lock, irqflags); + + /* init RAMFC. */ + nv_wv32(ch->bo, ch->ramfc + 0x00, 0); + nv_wv32(ch->bo, ch->ramfc + 0x04, 0); + nv_wv32(ch->bo, ch->ramfc + 0x08, pb_start); + nv_wv32(ch->bo, ch->ramfc + 0x0c, pb_start >> 32); + nv_wv32(ch->bo, ch->ramfc + 0x10, pb_start); + nv_wv32(ch->bo, ch->ramfc + 0x14, pb_start >> 32); + nv_wv32(ch->bo, ch->ramfc + 0x18, 0); + nv_wv32(ch->bo, ch->ramfc + 0x1c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x20, 0); + nv_wv32(ch->bo, ch->ramfc + 0x24, 0); + nv_wv32(ch->bo, ch->ramfc + 0x28, 0); + nv_wv32(ch->bo, ch->ramfc + 0x2c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x30, 0); + nv_wv32(ch->bo, ch->ramfc + 0x34, 0); + nv_wv32(ch->bo, ch->ramfc + 0x38, 0); + nv_wv32(ch->bo, ch->ramfc + 0x3c, 0x003f6078); + nv_wv32(ch->bo, ch->ramfc + 0x40, 0); + nv_wv32(ch->bo, ch->ramfc + 0x44, 0x2101ffff); + nv_wv32(ch->bo, ch->ramfc + 0x48, pb_inst); + nv_wv32(ch->bo, ch->ramfc + 0x4c, 0xffffffff); + nv_wv32(ch->bo, ch->ramfc + 0x50, 0); + nv_wv32(ch->bo, ch->ramfc + 0x54, 0); + nv_wv32(ch->bo, ch->ramfc + 0x58, 0); + nv_wv32(ch->bo, ch->ramfc + 0x5c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x60, 0x7fffffff); + nv_wv32(ch->bo, ch->ramfc + 0x64, 0); + nv_wv32(ch->bo, ch->ramfc + 0x68, 0); + nv_wv32(ch->bo, ch->ramfc + 0x6c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x70, 0); + nv_wv32(ch->bo, ch->ramfc + 0x74, 0); + nv_wv32(ch->bo, ch->ramfc + 0x78, 0); + nv_wv32(ch->bo, ch->ramfc + 0x7c, 0x30000000 ^ slimask); + nv_wv32(ch->bo, ch->ramfc + 0x80, 0x4000000 | ch->ramht.offset >> 4 | (ch->ramht.bits - 9) << 27); + nv_wv32(ch->bo, ch->ramfc + 0x84, 0); + + if (dev_priv->chipset != 0x50) { + nv_wv32(ch->bo, ch->ramfc + 0x88, ch->cache->start >> 10); + nv_wv32(ch->bo, ch->ramfc + 0x8c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x90, 0); + nv_wv32(ch->bo, ch->ramfc + 0x94, 0); + nv_wv32(ch->bo, ch->ramfc + 0x98, ch->bo->start >> 12); + + nv_wr32(dev, 0x2600 + ch->cid * 4, 0x80000000 | (ch->bo->start + ch->ramfc) >> 8); + } else { + nv_wr32(dev, 0x2600 + ch->cid * 4, 0x80000000 | ch->bo->start >> 12); + } + + nv50_fifo_playlist_update(dev); + spin_unlock_irqrestore(&fifo->lock, irqflags); + + return 0; +} + +int nv50_fifo_chan_init_ib (struct pscnv_chan *ch, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t ib_start, uint32_t ib_order) { + struct drm_device *dev = ch->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv50_fifo_engine *fifo = nv50_fifo(dev_priv->fifo); + unsigned long irqflags; + uint32_t pb_inst; + + /* XXX: verify that we get a DMA object. */ + pb_inst = pscnv_ramht_find(&ch->ramht, pb_handle); + if (!pb_inst || pb_inst & 0xffff0000) { + pscnv_chan_unref(ch); + return -ENOENT; + } + + spin_lock_irqsave(&fifo->lock, irqflags); + + /* init RAMFC. */ + nv_wv32(ch->bo, ch->ramfc + 0x00, 0); + nv_wv32(ch->bo, ch->ramfc + 0x04, 0); + nv_wv32(ch->bo, ch->ramfc + 0x08, 0); + nv_wv32(ch->bo, ch->ramfc + 0x0c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x10, 0); + nv_wv32(ch->bo, ch->ramfc + 0x14, 0); + nv_wv32(ch->bo, ch->ramfc + 0x18, 0); + nv_wv32(ch->bo, ch->ramfc + 0x1c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x20, 0); + nv_wv32(ch->bo, ch->ramfc + 0x24, 0); + nv_wv32(ch->bo, ch->ramfc + 0x28, 0); + nv_wv32(ch->bo, ch->ramfc + 0x2c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x30, 0); + nv_wv32(ch->bo, ch->ramfc + 0x34, 0); + nv_wv32(ch->bo, ch->ramfc + 0x38, 0); + nv_wv32(ch->bo, ch->ramfc + 0x3c, 0x403f6078); + nv_wv32(ch->bo, ch->ramfc + 0x40, 0); + nv_wv32(ch->bo, ch->ramfc + 0x44, 0x2101ffff); + nv_wv32(ch->bo, ch->ramfc + 0x48, pb_inst); + nv_wv32(ch->bo, ch->ramfc + 0x4c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x50, ib_start); + nv_wv32(ch->bo, ch->ramfc + 0x54, ib_start >> 32 | ib_order << 16); + nv_wv32(ch->bo, ch->ramfc + 0x58, 0); + nv_wv32(ch->bo, ch->ramfc + 0x5c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x60, 0x7fffffff); + nv_wv32(ch->bo, ch->ramfc + 0x64, 0); + nv_wv32(ch->bo, ch->ramfc + 0x68, 0); + nv_wv32(ch->bo, ch->ramfc + 0x6c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x70, 0); + nv_wv32(ch->bo, ch->ramfc + 0x74, 0); + nv_wv32(ch->bo, ch->ramfc + 0x78, 0); + nv_wv32(ch->bo, ch->ramfc + 0x7c, 0x30000000 ^ slimask); + nv_wv32(ch->bo, ch->ramfc + 0x80, 0x4000000 | ch->ramht.offset >> 4 | (ch->ramht.bits - 9) << 27); + nv_wv32(ch->bo, ch->ramfc + 0x84, 0); + + if (dev_priv->chipset != 0x50) { + nv_wv32(ch->bo, ch->ramfc + 0x88, ch->cache->start >> 10); + nv_wv32(ch->bo, ch->ramfc + 0x8c, 0); + nv_wv32(ch->bo, ch->ramfc + 0x90, 0); + nv_wv32(ch->bo, ch->ramfc + 0x94, 0); + nv_wv32(ch->bo, ch->ramfc + 0x98, ch->bo->start >> 12); + + nv_wr32(dev, 0x2600 + ch->cid * 4, 0x80000000 | (ch->bo->start + ch->ramfc) >> 8); + } else { + nv_wr32(dev, 0x2600 + ch->cid * 4, 0x80000000 | ch->bo->start >> 12); + } + + nv50_fifo_playlist_update(dev); + spin_unlock_irqrestore(&fifo->lock, irqflags); + + pscnv_chan_unref(ch); + return 0; +} + +struct pscnv_enumval { + int value; + char *name; + void *data; +}; + +static struct pscnv_enumval dma_pusher_errors[] = { + { 1, "CALL_OVERFLOW", 0 }, + { 2, "INVALID_METHOD", 0 }, + { 3, "RET_UNDERFLOW", 0 }, + { 4, "INVALID_COMMAND", 0 }, + { 5, "IB", 0 }, + { 6, "MEM_FAULT", 0 }, + + { 0, 0, 0 }, +}; + +static struct pscnv_enumval semaphore_errors[] = { + { 1, "OFFSET_UNALIGNED", 0 }, + { 2, "INVALID_STATE", 0 }, + { 3, "OFFSET_TOO_LARGE", 0 }, + { 4, "MEM_FAULT", 0 }, + + { 0, 0, 0 }, +}; + +static struct pscnv_enumval *pscnv_enum_find (struct pscnv_enumval *list, int val) { + while (list->value != val && list->name) + list++; + if (list->name) + return list; + else + return 0; +} + +void nv50_fifo_irq_handler(struct drm_device *dev, int irq) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv50_fifo_engine *fifo = nv50_fifo(dev_priv->fifo); + uint32_t status; + int ch; + unsigned long flags; + spin_lock_irqsave(&fifo->lock, flags); + status = nv_rd32(dev, 0x2100); + ch = nv_rd32(dev, 0x3204) & 0x7f; + if (status & 0x00000001) { + uint32_t get = nv_rd32(dev, 0x3270); + uint32_t addr = nv_rd32(dev, 0x90000 + (get & 0x7fc) * 2); + uint32_t data = nv_rd32(dev, 0x90000 + (get & 0x7fc) * 2 + 4); + uint32_t pull = nv_rd32(dev, 0x3250); + const char *reason = 0; + if (pull & 0x10) + reason = "NO_HASH"; + if (pull & 0x100) + reason = "EMPTY_SUBCHAN"; + if (reason) + NV_ERROR(dev, "PFIFO_CACHE_ERROR [%s]: ch %d subch %d addr %04x data %08x\n", reason, ch, (addr >> 13) & 7, addr & 0x1ffc, data); + else + NV_ERROR(dev, "PFIFO_CACHE_ERROR [%08x]: ch %d subch %d addr %04x data %08x\n", pull, ch, (addr >> 13) & 7, addr & 0x1ffc, data); + get += 4; + nv_wr32(dev, 0x3270, get); + nv_wr32(dev, 0x2100, 0x00000001); + nv_wr32(dev, 0x3250, 1); + status &= ~0x00000001; + } + if (status & 0x00000010) { + NV_ERROR(dev, "PFIFO BAR fault!\n"); + nv_wr32(dev, 0x2100, 0x00000010); + status &= ~0x00000010; + } + if (status & 0x00000040) { + NV_ERROR(dev, "PFIFO PEEPHOLE fault!\n"); + nv_wr32(dev, 0x2100, 0x00000040); + status &= ~0x00000040; + } + if (status & 0x00001000) { + uint32_t get = nv_rd32(dev, 0x3244); + uint32_t gethi = nv_rd32(dev, 0x3328); + /* XXX: yup. a race. */ + uint32_t put = nv_rd32(dev, 0x3240); + uint32_t puthi = nv_rd32(dev, 0x3320); + uint32_t ib_get = nv_rd32(dev, 0x3334); + uint32_t ib_put = nv_rd32(dev, 0x3330); + uint32_t dma_state = nv_rd32(dev, 0x3228); + uint32_t dma_push = nv_rd32(dev, 0x3220); + uint32_t st1 = nv_rd32(dev, 0x32a0); + uint32_t st2 = nv_rd32(dev, 0x32a4); + uint32_t st3 = nv_rd32(dev, 0x32a8); + uint32_t st4 = nv_rd32(dev, 0x32ac); + uint32_t len = nv_rd32(dev, 0x3364); + struct pscnv_enumval *ev; + ev = pscnv_enum_find(dma_pusher_errors, dma_state >> 29); + NV_ERROR(dev, "PFIFO_DMA_PUSHER [%s]: ch %d addr %02x%08x [PUT %02x%08x], IB %08x [PUT %08x] status %08x len %08x push %08x shadow %08x %08x %08x %08x\n", + ev?ev->name:"?", ch, gethi, get, puthi, put, ib_get, ib_put, dma_state, len, dma_push, st1, st2, st3, st4); + if (get != put || gethi != puthi) { + nv_wr32(dev, 0x3244, put); + nv_wr32(dev, 0x3328, puthi); + } else if (ib_get != ib_put) { + nv_wr32(dev, 0x3334, ib_put); + } else { + nv_wr32(dev, 0x3330, 0); + nv_wr32(dev, 0x3334, 0); + } + nv_wr32(dev, 0x3228, 0); + nv_wr32(dev, 0x3364, 0); + nv_wr32(dev, 0x3220, 1); + nv_wr32(dev, 0x2100, 0x00001000); + status &= ~0x00001000; + } + if (status & 0x00100000) { + uint32_t get = nv_rd32(dev, 0x3270); + uint32_t addr = nv_rd32(dev, 0x90000 + (get & 0x7fc) * 2); + uint32_t data = nv_rd32(dev, 0x90000 + (get & 0x7fc) * 2 + 4); + uint32_t pull = nv_rd32(dev, 0x3250); + struct pscnv_enumval *ev; + ev = pscnv_enum_find(semaphore_errors, (pull >> 20) & 0xf); + if (dev_priv->chipset > 0x50) { + /* the SEMAPHORE fuckup special #2 */ + uint32_t sem_lo = nv_rd32(dev, 0x3404); + if (sem_lo & 3) { + nv_wr32(dev, 0x3404, 0); + get -= 4; + get &= 0xffc; + addr = 0x14; + data = sem_lo; + } + } + NV_ERROR(dev, "PFIFO_SEMAPHORE [%s]: ch %d subch %d addr %04x data %08x status %08x\n", ev?ev->name:"?", ch, (addr >> 13) & 7, addr & 0x1ffc, data, pull); + get += 4; + nv_wr32(dev, 0x3270, get); + nv_wr32(dev, 0x3250, 1); + nv_wr32(dev, 0x2100, 0x00100000); + status &= ~0x00100000; + } + if (status) { + NV_ERROR(dev, "Unknown PFIFO interrupt %08x\n", status); + nv_wr32(dev, 0x2100, status); + } + nv50_vm_trap(dev); + spin_unlock_irqrestore(&fifo->lock, flags); +} diff --git a/driver/pscnv/nv50_gpio.c b/driver/pscnv/nv50_gpio.c new file mode 100644 index 00000000..b2fab2bf --- /dev/null +++ b/driver/pscnv/nv50_gpio.c @@ -0,0 +1,111 @@ +/* + * Copyright 2010 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_hw.h" + +static int +nv50_gpio_location(struct dcb_gpio_entry *gpio, uint32_t *reg, uint32_t *shift) +{ + const uint32_t nv50_gpio_reg[4] = { 0xe104, 0xe108, 0xe280, 0xe284 }; + + if (gpio->line >= 32) + return -EINVAL; + + *reg = nv50_gpio_reg[gpio->line >> 3]; + *shift = (gpio->line & 7) << 2; + return 0; +} + +int +nv50_gpio_get(struct drm_device *dev, enum dcb_gpio_tag tag) +{ + struct dcb_gpio_entry *gpio; + uint32_t r, s, v; + + gpio = nouveau_bios_gpio_entry(dev, tag); + if (!gpio) + return -ENOENT; + + if (nv50_gpio_location(gpio, &r, &s)) + return -EINVAL; + + v = nv_rd32(dev, r) >> (s + 2); + return ((v & 1) == (gpio->state[1] & 1)); +} + +int +nv50_gpio_set(struct drm_device *dev, enum dcb_gpio_tag tag, int state) +{ + struct dcb_gpio_entry *gpio; + uint32_t r, s, v; + + gpio = nouveau_bios_gpio_entry(dev, tag); + if (!gpio) + return -ENOENT; + + if (nv50_gpio_location(gpio, &r, &s)) + return -EINVAL; + + v = nv_rd32(dev, r) & ~(0x3 << s); + v |= (gpio->state[state] ^ 2) << s; + nv_wr32(dev, r, v); + return 0; +} + +void +nv50_gpio_irq_enable(struct drm_device *dev, enum dcb_gpio_tag tag, bool on) +{ + struct dcb_gpio_entry *gpio; + u32 reg, mask; + + gpio = nouveau_bios_gpio_entry(dev, tag); + if (!gpio) { + NV_ERROR(dev, "gpio tag 0x%02x not found\n", tag); + return; + } + + reg = gpio->line < 16 ? 0xe050 : 0xe070; + mask = 0x00010001 << (gpio->line & 0xf); + + nv_wr32(dev, reg + 4, mask); + nv_mask(dev, reg + 0, mask, on ? mask : 0); +} + +int +nv50_gpio_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + /* disable, and ack any pending gpio interrupts */ + nv_wr32(dev, 0xe050, 0x00000000); + nv_wr32(dev, 0xe054, 0xffffffff); + if (dev_priv->chipset >= 0x90) { + nv_wr32(dev, 0xe070, 0x00000000); + nv_wr32(dev, 0xe074, 0xffffffff); + } + + return 0; +} diff --git a/driver/pscnv/nv50_graph.c b/driver/pscnv/nv50_graph.c new file mode 100644 index 00000000..84c36374 --- /dev/null +++ b/driver/pscnv/nv50_graph.c @@ -0,0 +1,1006 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drm.h" +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_grctx.h" +#include "pscnv_engine.h" +#include "pscnv_chan.h" +#include "nv50_chan.h" +#include "nv50_vm.h" + +struct nv50_graph_engine { + struct pscnv_engine base; + spinlock_t lock; + uint32_t grctx_size; +}; + +struct nv50_graph_chan { + struct pscnv_bo *grctx; +}; + +#define nv50_graph(x) container_of(x, struct nv50_graph_engine, base) + +static int nv50_graph_oclasses[] = { + /* NULL */ + 0x0030, + /* m2mf */ + 0x5039, + /* NV01-style 2d */ + 0x0012, + 0x0019, + 0x0043, + 0x0044, + 0x004a, + 0x0057, + 0x005d, + 0x005f, + 0x0072, + 0x305c, + 0x3064, + 0x3066, + 0x307b, + 0x308a, + 0x5062, + 0x5089, + /* NV50-style 2d */ + 0x502d, + /* compute */ + 0x50c0, + /* 3d */ + 0x5097, + /* list terminator */ + 0 +}; + +static int nv84_graph_oclasses[] = { + /* NULL */ + 0x0030, + /* m2mf */ + 0x5039, + /* NV50-style 2d */ + 0x502d, + /* compute */ + 0x50c0, + /* 3d */ + 0x5097, + 0x8297, + /* list terminator */ + 0 +}; + +static int nva0_graph_oclasses[] = { + /* NULL */ + 0x0030, + /* m2mf */ + 0x5039, + /* NV50-style 2d */ + 0x502d, + /* compute */ + 0x50c0, + /* 3d */ + 0x8397, + /* list terminator */ + 0 +}; + +static int nva3_graph_oclasses[] = { + /* NULL */ + 0x0030, + /* m2mf */ + 0x5039, + /* NV50-style 2d */ + 0x502d, + /* compute */ + 0x50c0, + 0x85c0, + /* 3d */ + 0x8597, + /* list terminator */ + 0 +}; + +static int nvaf_graph_oclasses[] = { + /* NULL */ + 0x0030, + /* m2mf */ + 0x5039, + /* NV50-style 2d */ + 0x502d, + /* compute */ + 0x50c0, + 0x85c0, + /* 3d */ + 0x8697, + /* list terminator */ + 0 +}; + +void nv50_graph_takedown(struct pscnv_engine *eng); +void nv50_graph_irq_handler(struct drm_device *dev, int irq); +int nv50_graph_tlb_flush(struct pscnv_engine *eng, struct pscnv_vspace *vs); +int nv86_graph_tlb_flush(struct pscnv_engine *eng, struct pscnv_vspace *vs); +int nv50_graph_chan_alloc(struct pscnv_engine *eng, struct pscnv_chan *ch); +void nv50_graph_chan_free(struct pscnv_engine *eng, struct pscnv_chan *ch); +void nv50_graph_chan_kill(struct pscnv_engine *eng, struct pscnv_chan *ch); +int nv50_graph_chan_obj_new(struct pscnv_engine *eng, struct pscnv_chan *ch, uint32_t handle, uint32_t oclass, uint32_t flags); + +int nv50_graph_init(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t units = nv_rd32(dev, 0x1540); + struct nouveau_grctx ctx = {}; + int ret, i; + uint32_t *cp; + struct nv50_graph_engine *res = kzalloc(sizeof *res, GFP_KERNEL); + + if (!res) { + NV_ERROR(dev, "PGRAPH: Couldn't allocate engine!\n"); + return -ENOMEM; + } + + res->base.dev = dev; + if (dev_priv->chipset == 0x50) + res->base.oclasses = nv50_graph_oclasses; + else if (dev_priv->chipset < 0xa0) + res->base.oclasses = nv84_graph_oclasses; + else if (dev_priv->chipset == 0xa0 || + (dev_priv->chipset >= 0xaa && dev_priv->chipset <= 0xac)) + res->base.oclasses = nva0_graph_oclasses; + else if (dev_priv->chipset < 0xaa) + res->base.oclasses = nva3_graph_oclasses; + else + res->base.oclasses = nvaf_graph_oclasses; + res->base.takedown = nv50_graph_takedown; + if (dev_priv->chipset == 0x86) + res->base.tlb_flush = nv86_graph_tlb_flush; + else + res->base.tlb_flush = nv50_graph_tlb_flush; + res->base.chan_alloc = nv50_graph_chan_alloc; + res->base.chan_kill = nv50_graph_chan_kill; + res->base.chan_free = nv50_graph_chan_free; + res->base.chan_obj_new = nv50_graph_chan_obj_new; + spin_lock_init(&res->lock); + + /* reset everything */ + nv_wr32(dev, 0x200, 0xffffefff); + nv_wr32(dev, 0x200, 0xffffffff); + + /* reset and enable traps & interrupts */ + nv_wr32(dev, 0x400804, 0xc0000000); /* DISPATCH */ + nv_wr32(dev, 0x406800, 0xc0000000); /* M2MF */ + nv_wr32(dev, 0x400c04, 0xc0000000); /* VFETCH */ + nv_wr32(dev, 0x401800, 0xc0000000); /* STRMOUT */ + nv_wr32(dev, 0x405018, 0xc0000000); /* CCACHE */ + nv_wr32(dev, 0x402000, 0xc0000000); /* CLIPID */ + for (i = 0; i < 16; i++) + if (units & 1 << i) { + if (dev_priv->chipset < 0xa0) { + nv_wr32(dev, 0x408900 + (i << 12), 0xc0000000); /* TEX */ + nv_wr32(dev, 0x408e08 + (i << 12), 0xc0000000); /* TPDMA */ + nv_wr32(dev, 0x408314 + (i << 12), 0xc0000000); /* MPC */ + } else { + nv_wr32(dev, 0x408600 + (i << 11), 0xc0000000); /* TEX */ + nv_wr32(dev, 0x408708 + (i << 11), 0xc0000000); /* TPDMA */ + nv_wr32(dev, 0x40831c + (i << 11), 0xc0000000); /* MPC */ + } + } + nv_wr32(dev, 0x400108, -1); /* TRAP */ + nv_wr32(dev, 0x400100, -1); /* INTR */ + + /* set ctxprog flags */ + nv_wr32(dev, 0x400824, 0x00004000); + + /* enable FIFO access */ + /* XXX: figure out what exactly is bit 16. All I know is that it's + * needed for QUERYs to work. */ + nv_wr32(dev, 0x400500, 0x00010001); + + /* init ZCULL... or something */ + nv_wr32(dev, 0x402ca8, 0x00000800); + + /* init DEBUG regs */ + /* XXX: look at the other two regs and values everyone uses. pick something. */ + nv_wr32(dev, 0x40008c, 0x00000004); + + /* init and upload ctxprog */ + cp = ctx.data = kmalloc (512 * 4, GFP_KERNEL); + if (!ctx.data) { + NV_ERROR (dev, "PGRAPH: Couldn't allocate ctxprog!\n"); + kfree(res); + return -ENOMEM; + } + ctx.ctxprog_max = 512; + ctx.dev = dev; + ctx.mode = NOUVEAU_GRCTX_PROG; + if ((ret = nv50_grctx_init(&ctx))) { + kfree(ctx.data); + kfree(res); + return ret; + } + res->grctx_size = ctx.ctxvals_pos * 4; + nv_wr32(dev, 0x400324, 0); + for (i = 0; i < ctx.ctxprog_len; i++) + nv_wr32(dev, 0x400328, cp[i]); + kfree(ctx.data); + + /* mark no channel loaded */ + /* XXX: is that fully correct? */ + nv_wr32(dev, 0x40032c, 0); + nv_wr32(dev, 0x400784, 0); + nv_wr32(dev, 0x400320, 4); + + dev_priv->engines[PSCNV_ENGINE_GRAPH] = &res->base; + + nouveau_irq_register(dev, 12, nv50_graph_irq_handler); + + nv_wr32(dev, 0x400138, -1); /* TRAP_EN */ + nv_wr32(dev, 0x40013c, -1); /* INTR_EN */ + return 0; +} + +void nv50_graph_takedown(struct pscnv_engine *eng) { + struct drm_nouveau_private *dev_priv = eng->dev->dev_private; + nv_wr32(eng->dev, 0x400138, 0); /* TRAP_EN */ + nv_wr32(eng->dev, 0x40013c, 0); /* INTR_EN */ + nouveau_irq_unregister(eng->dev, 12); + /* XXX */ + kfree(eng); + dev_priv->engines[PSCNV_ENGINE_GRAPH] = 0; +} + +int nv50_graph_chan_alloc(struct pscnv_engine *eng, struct pscnv_chan *ch) { + struct drm_device *dev = eng->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv50_graph_engine *graph = nv50_graph(eng); + struct nouveau_grctx ctx = {}; + uint32_t hdr; + uint64_t limit; + int i; + struct nv50_graph_chan *grch = kzalloc(sizeof *grch, GFP_KERNEL); + + if (!grch) { + NV_ERROR(dev, "PGRAPH: Couldn't allocate channel!\n"); + return -ENOMEM; + } + + if (dev_priv->chipset == 0x50) + hdr = 0x200; + else + hdr = 0x20; + grch->grctx = pscnv_mem_alloc(dev, graph->grctx_size, PSCNV_GEM_CONTIG, 0, 0x97c07e47); + if (!grch->grctx) { + NV_ERROR(dev, "PGRAPH: No VRAM for context!\n"); + kfree(grch); + return -ENOMEM; + } + for (i = 0; i < graph->grctx_size; i += 4) + nv_wv32(grch->grctx, i, 0); + ctx.dev = dev; + ctx.mode = NOUVEAU_GRCTX_VALS; + ctx.data = grch->grctx; + nv50_grctx_init(&ctx); + limit = grch->grctx->start + graph->grctx_size - 1; + + nv_wv32(ch->bo, hdr + 0x00, 0x00190000); + nv_wv32(ch->bo, hdr + 0x04, limit); + nv_wv32(ch->bo, hdr + 0x08, grch->grctx->start); + nv_wv32(ch->bo, hdr + 0x0c, (limit >> 32) << 24 | (grch->grctx->start >> 32)); + nv_wv32(ch->bo, hdr + 0x10, 0); + nv_wv32(ch->bo, hdr + 0x14, 0); + dev_priv->vm->bar_flush(dev); + + nv50_vs(ch->vspace)->engref[PSCNV_ENGINE_GRAPH]++; + ch->engdata[PSCNV_ENGINE_GRAPH] = grch; + return 0; +} + +int nv50_graph_tlb_flush(struct pscnv_engine *eng, struct pscnv_vspace *vs) { + return nv50_vm_flush(eng->dev, 0); +} + +int nv86_graph_tlb_flush(struct pscnv_engine *eng, struct pscnv_vspace *vs) { + /* NV86 TLB fuckup special workaround. */ + struct drm_device *dev = eng->dev; + uint64_t start; + /* initial guess... */ + uint32_t mask380 = 0xffffffff; + uint32_t mask384 = 0xffffffff; + uint32_t mask388 = 0xffffffff; + struct nv50_graph_engine *graph = nv50_graph(eng); + int ret; + unsigned long flags; + spin_lock_irqsave(&graph->lock, flags); + nv_wr32(dev, 0x400500, 0); + start = nv04_timer_read(dev); + while ((nv_rd32(dev, 0x400380) & mask380) || (nv_rd32(dev, 0x400384) & mask384) || (nv_rd32(dev, 0x400388) & mask388)) { + if (nv04_timer_read(dev) - start >= 2000000000) { + /* if you see this message, mask* above probably need to be adjusted to not contain the bits you see failing */ + NV_ERROR(dev, "PGRAPH: idle wait for TLB flush fail: %08x %08x %08x [%08x]!\n", nv_rd32(dev, 0x400380), nv_rd32(dev, 0x400384), nv_rd32(dev, 0x400388), nv_rd32(dev, 0x400700)); + break; + } + } + ret = nv50_vm_flush(dev, 0); + nv_wr32(dev, 0x400500, 0x10001); + spin_unlock_irqrestore(&graph->lock, flags); + return ret; +} + +void nv50_graph_chan_kill(struct pscnv_engine *eng, struct pscnv_chan *ch) { + struct drm_device *dev = eng->dev; + struct nv50_graph_engine *graph = nv50_graph(eng); + uint64_t start; + unsigned long flags; + spin_lock_irqsave(&graph->lock, flags); + start = nv04_timer_read(dev); + /* disable PFIFO access */ + nv_wr32(dev, 0x400500, 0); + /* tell ctxprog to hang in sync point, if it's executing */ + nv_wr32(dev, 0x400830, 1); + /* make sure that ctxprog either isn't executing, or is waiting at the + * sync point. */ + while ((nv_rd32(dev, 0x400300) & 1) && !(nv_rd32(dev, 0x400824) & 0x80000000)) { + if (nv04_timer_read(dev) - start >= 2000000000) { + NV_ERROR(dev, "ctxprog wait fail!\n"); + break; + } + } + /* check if the channel we're freeing is active on PGRAPH. */ + if (nv_rd32(dev, 0x40032c) == (0x80000000 | ch->bo->start >> 12)) { + NV_INFO(dev, "Kicking channel %d off PGRAPH.\n", ch->cid); + /* DIE */ + nv_wr32(dev, 0x400040, -1); + nv_wr32(dev, 0x400040, 0); + /* no active channel now. */ + nv_wr32(dev, 0x40032c, 0); + /* if ctxprog was running, rewind it to the beginning. if it + * wasn't, this has no effect. */ + nv_wr32(dev, 0x400310, 0); + } + /* or maybe it was just going to be loaded in? */ + if (nv_rd32(dev, 0x400330) == (0x80000000 | ch->bo->start >> 12)) { + nv_wr32(dev, 0x400330, 0); + nv_wr32(dev, 0x400310, 0); + } + /* back to normal state. */ + nv_wr32(dev, 0x400830, 0); + nv_wr32(dev, 0x400500, 0x10001); + spin_unlock_irqrestore(&graph->lock, flags); +} + +void nv50_graph_chan_free(struct pscnv_engine *eng, struct pscnv_chan *ch) { + struct nv50_graph_chan *grch = ch->engdata[PSCNV_ENGINE_GRAPH]; + pscnv_mem_free(grch->grctx); + kfree(grch); + nv50_vs(ch->vspace)->engref[PSCNV_ENGINE_GRAPH]--; + ch->engdata[PSCNV_ENGINE_GRAPH] = 0; + nv50_graph_tlb_flush(eng, ch->vspace); +} + +int nv50_graph_chan_obj_new(struct pscnv_engine *eng, struct pscnv_chan *ch, uint32_t handle, uint32_t oclass, uint32_t flags) { + uint32_t inst = nv50_chan_iobj_new(ch, 0x10); + if (!inst) { + return -ENOMEM; + } + nv_wv32(ch->bo, inst, oclass); + nv_wv32(ch->bo, inst + 4, 0); + nv_wv32(ch->bo, inst + 8, 0); + nv_wv32(ch->bo, inst + 0xc, 0); + return pscnv_ramht_insert (&ch->ramht, handle, 0x100000 | inst >> 4); +} + +struct pscnv_enumval { + int value; + char *name; + void *data; +}; + +static struct pscnv_enumval dispatch_errors[] = { + { 3, "INVALID_OPERATION", 0 }, + { 4, "INVALID_VALUE", 0 }, + { 5, "INVALID_ENUM", 0 }, + + { 8, "INVALID_OBJECT", 0 }, + { 9, "READ_ONLY_OBJECT", 0 }, + { 0xa, "SUPERVISOR_OBJECT", 0 }, + { 0xb, "INVALID_ADDRESS_ALIGNMENT", 0 }, + { 0xc, "INVALID_BITFIELD", 0 }, + { 0xd, "BEGIN_END_ACTIVE", 0 }, + { 0xe, "SEMANTIC_COLOR_BACK_OVER_LIMIT", 0 }, + { 0xf, "VIEWPORT_ID_NEEDS_GP", 0 }, + { 0x10, "RT_DOUBLE_BIND", 0 }, + { 0x11, "RT_TYPES_MISMATCH", 0 }, + { 0x12, "RT_LINEAR_WITH_ZETA", 0 }, + + { 0x15, "FP_TOO_FEW_REGS", 0 }, + { 0x16, "ZETA_FORMAT_CSAA_MISMATCH", 0 }, + { 0x17, "RT_LINEAR_WITH_MSAA", 0 }, + { 0x18, "FP_INTERPOLANT_START_OVER_LIMIT", 0 }, + { 0x19, "SEMANTIC_LAYER_OVER_LIMIT", 0 }, + { 0x1a, "RT_INVALID_ALIGNMENT", 0 }, + { 0x1b, "SAMPLER_OVER_LIMIT", 0 }, + { 0x1c, "TEXTURE_OVER_LIMIT", 0 }, + + { 0x1e, "GP_TOO_MANY_OUTPUTS", 0 }, + { 0x1f, "RT_BPP128_WITH_MS8", 0 }, + + { 0x21, "Z_OUT_OF_BOUNDS", 0 }, + + { 0x23, "M2MF_OUT_OF_BOUNDS", 0 }, + + { 0x27, "CP_MORE_PARAMS_THAN_SHARED", 0 }, + { 0x28, "CP_NO_REG_SPACE_STRIPED", 0 }, + { 0x29, "CP_NO_REG_SPACE_PACKED", 0 }, + { 0x2a, "CP_NOT_ENOUGH_WARPS", 0 }, + { 0x2b, "CP_BLOCK_SIZE_MISMATCH", 0 }, + { 0x2c, "CP_NOT_ENOUGH_LOCAL_WARPS", 0 }, + { 0x2d, "CP_NOT_ENOUGH_STACK_WARPS", 0 }, + { 0x2e, "CP_NO_BLOCKDIM_LATCH", 0 }, + + { 0x31, "ENG2D_FORMAT_MISMATCH", 0 }, + + { 0x3f, "PRIMITIVE_ID_NEEDS_GP", 0 }, + + { 0x44, "SEMANTIC_VIEWPORT_OVER_LIMIT", 0 }, + { 0x45, "SEMANTIC_COLOR_FRONT_OVER_LIMIT", 0 }, + { 0x46, "LAYER_ID_NEEDS_GP", 0 }, + { 0x47, "SEMANTIC_CLIP_OVER_LIMIT", 0 }, + { 0x48, "SEMANTIC_PTSZ_OVER_LIMIT", 0 }, + + { 0, 0, 0 }, +}; + +static struct pscnv_enumval *pscnv_enum_find (struct pscnv_enumval *list, int val) { + while (list->value != val && list->name) + list++; + if (list->name) + return list; + else + return 0; +} + +void nv50_graph_tex_trap(struct drm_device *dev, int cid, int tp) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t staddr, status; + uint32_t e04, e08, e0c, e10; + uint64_t addr; + if (dev_priv->chipset < 0xa0) + staddr = 0x408900 + tp * 0x1000; + else + staddr = 0x408600 + tp * 0x800; + status = nv_rd32(dev, staddr) & 0x7fffffff; + e04 = nv_rd32(dev, staddr + 4); + e08 = nv_rd32(dev, staddr + 8); + e0c = nv_rd32(dev, staddr + 0xc); + e10 = nv_rd32(dev, staddr + 0x10); + addr = (uint64_t)e08 << 8; + if (!(status & 1)) { // seems always set... + NV_ERROR(dev, "PGRAPH_TRAP_TEXTURE: ch %d TP %d status %08x [no 1!]\n", cid, tp, status); + } + status &= ~1; + if (status & 2) { + NV_ERROR(dev, "PGRAPH_TRAP_TEXTURE: ch %d TP %d FAULT at %llx\n", cid, tp, addr); + status &= ~2; + } + if (status & 4) { + NV_ERROR(dev, "PGRAPH_TRAP_TEXTURE: ch %d TP %d STORAGE_TYPE_MISMATCH type %02x\n", cid, tp, e10 >> 5 & 0x7f); + status &= ~4; + } + if (status & 8) { + NV_ERROR(dev, "PGRAPH_TRAP_TEXTURE: ch %d TP %d LINEAR_MISMATCH type %02x\n", cid, tp, e10 >> 5 & 0x7f); + status &= ~8; + } + if (status & 0x20) { + NV_ERROR(dev, "PGRAPH_TRAP_TEXTURE: ch %d TP %d WRONG_MEMTYPE type %02x\n", cid, tp, e10 >> 5 & 0x7f); + status &= ~0x20; + } + if (status) { + NV_ERROR(dev, "PGRAPH_TRAP_TEXTURE: ch %d TP %d status %08x\n", cid, tp, status); + } + NV_ERROR(dev, "magic: %08x %08x %08x %08x\n", e04, e08, e0c, e10); + nv_wr32(dev, staddr, 0xc0000000); +} + +void nv50_graph_mp_trap(struct drm_device *dev, int cid, int tp, int mp) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t mpaddr, mp10, status, pc, oplo, ophi; + if (dev_priv->chipset < 0xa0) + mpaddr = 0x408200 + tp * 0x1000 + mp * 0x80; + else + mpaddr = 0x408100 + tp * 0x800 + mp * 0x80; + mp10 = nv_rd32(dev, mpaddr + 0x10); + status = nv_rd32(dev, mpaddr + 0x14); + nv_rd32(dev, mpaddr + 0x20); + pc = nv_rd32(dev, mpaddr + 0x24); + oplo = nv_rd32(dev, mpaddr + 0x70); + ophi = nv_rd32(dev, mpaddr + 0x74); + if (!status) + return; + if (status & 1) { + NV_ERROR(dev, "PGRAPH_TRAP_MP: ch %d TP %d MP %d STACK_UNDERFLOW at %06x warp %d op %08x %08x\n", cid, tp, mp, pc & 0xffffff, pc >> 24, oplo, ophi); + status &= ~1; + } + if (status & 2) { + NV_ERROR(dev, "PGRAPH_TRAP_MP: ch %d TP %d MP %d STACK_MISMATCH at %06x warp %d op %08x %08x\n", cid, tp, mp, pc & 0xffffff, pc >> 24, oplo, ophi); + status &= ~2; + } + if (status & 4) { + NV_ERROR(dev, "PGRAPH_TRAP_MP: ch %d TP %d MP %d QUADON_ACTIVE at %06x warp %d op %08x %08x\n", cid, tp, mp, pc & 0xffffff, pc >> 24, oplo, ophi); + status &= ~4; + } + if (status & 8) { + NV_ERROR(dev, "PGRAPH_TRAP_MP: ch %d TP %d MP %d TIMEOUT at %06x warp %d op %08x %08x\n", cid, tp, mp, pc & 0xffffff, pc >> 24, oplo, ophi); + status &= ~8; + } + if (status & 0x10) { + NV_ERROR(dev, "PGRAPH_TRAP_MP: ch %d TP %d MP %d INVALID_OPCODE at %06x warp %d op %08x %08x\n", cid, tp, mp, pc & 0xffffff, pc >> 24, oplo, ophi); + status &= ~0x10; + } + if (status & 0x40) { + NV_ERROR(dev, "PGRAPH_TRAP_MP: ch %d TP %d MP %d BREAKPOINT at %06x warp %d op %08x %08x\n", cid, tp, mp, pc & 0xffffff, pc >> 24, oplo, ophi); + status &= ~0x40; + } + if (status) { + NV_ERROR(dev, "PGRAPH_TRAP_MP: ch %d TP %d MP %d status %08x at %06x warp %d op %08x %08x\n", cid, tp, mp, status, pc & 0xffffff, pc >> 24, oplo, ophi); + } + nv_wr32(dev, mpaddr + 0x10, mp10); + nv_wr32(dev, mpaddr + 0x14, 0); +} + +void nv50_graph_mpc_trap(struct drm_device *dev, int cid, int tp) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t staddr, status; + if (dev_priv->chipset < 0xa0) + staddr = 0x408314 + tp * 0x1000; + else + staddr = 0x40831c + tp * 0x800; + status = nv_rd32(dev, staddr) & 0x7fffffff; + if (status & 1) { + NV_ERROR(dev, "PGRAPH_TRAP_MPC: ch %d TP %d LOCAL_LIMIT_READ\n", cid, tp); + status &= ~1; + } + if (status & 0x10) { + NV_ERROR(dev, "PGRAPH_TRAP_MPC: ch %d TP %d LOCAL_LIMIT_WRITE\n", cid, tp); + status &= ~0x10; + } + if (status & 0x40) { + NV_ERROR(dev, "PGRAPH_TRAP_MPC: ch %d TP %d STACK_LIMIT\n", cid, tp); + status &= ~0x40; + } + if (status & 0x100) { + NV_ERROR(dev, "PGRAPH_TRAP_MPC: ch %d TP %d GLOBAL_LIMIT_READ\n", cid, tp); + status &= ~0x100; + } + if (status & 0x1000) { + NV_ERROR(dev, "PGRAPH_TRAP_MPC: ch %d TP %d GLOBAL_LIMIT_WRITE\n", cid, tp); + status &= ~0x1000; + } + if (status & 0x10000) { + nv50_graph_mp_trap(dev, cid, tp, 0); + status &= ~0x10000; + } + if (status & 0x20000) { + nv50_graph_mp_trap(dev, cid, tp, 1); + status &= ~0x20000; + } + if (status & 0x40000) { + NV_ERROR(dev, "PGRAPH_TRAP_MPC: ch %d TP %d GLOBAL_LIMIT_RED\n", cid, tp); + status &= ~0x40000; + } + if (status & 0x400000) { + NV_ERROR(dev, "PGRAPH_TRAP_MPC: ch %d TP %d GLOBAL_LIMIT_ATOM\n", cid, tp); + status &= ~0x400000; + } + if (status & 0x4000000) { + nv50_graph_mp_trap(dev, cid, tp, 2); + status &= ~0x4000000; + } + if (status) { + NV_ERROR(dev, "PGRAPH_TRAP_MPC: ch %d TP %d status %08x\n", cid, tp, status); + } + nv_wr32(dev, staddr, 0xc0000000); +} + +void nv50_graph_tprop_trap(struct drm_device *dev, int cid, int tp) { + static const char *const tprop_tnames[14] = { + "RT0", + "RT1", + "RT2", + "RT3", + "RT4", + "RT5", + "RT6", + "RT7", + "ZETA", + "LOCAL", + "GLOBAL", + "STACK", + "DST2D", + "???", + }; + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t staddr, status; + uint32_t e0c, e10, e14, e18, e1c, e20, e24; + int surf; + uint64_t addr; + if (dev_priv->chipset < 0xa0) + staddr = 0x408e08 + tp * 0x1000; + else + staddr = 0x408708 + tp * 0x800; + status = nv_rd32(dev, staddr) & 0x7fffffff; + e0c = nv_rd32(dev, staddr + 4); + e10 = nv_rd32(dev, staddr + 8); + e14 = nv_rd32(dev, staddr + 0xc); + e18 = nv_rd32(dev, staddr + 0x10); + e1c = nv_rd32(dev, staddr + 0x14); + e20 = nv_rd32(dev, staddr + 0x18); + e24 = nv_rd32(dev, staddr + 0x1c); + surf = e24 >> 0x18 & 0xf; + addr = e10 | (uint64_t)e14 << 32; + if (surf > 13) + surf = 13; + if (status & 0x4) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s SURF_WIDTH_OVERRUN\n", cid, tp, tprop_tnames[surf]); + status &= ~0x4; + } + if (status & 0x8) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s SURF_HEIGHT_OVERRUN\n", cid, tp, tprop_tnames[surf]); + status &= ~0x8; + } + if (status & 0x10) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s DST2D_FAULT at %llx\n", cid, tp, tprop_tnames[surf], addr); + status &= ~0x10; + } + if (status & 0x20) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s ZETA_FAULT at %llx\n", cid, tp, tprop_tnames[surf], addr); + status &= ~0x20; + } + if (status & 0x40) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s RT_FAULT at %llx\n", cid, tp, tprop_tnames[surf], addr); + status &= ~0x40; + } + if (status & 0x80) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s CUDA_FAULT at %llx\n", cid, tp, tprop_tnames[surf], addr); + status &= ~0x80; + } + if (status & 0x100) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s DST2D_STORAGE_TYPE_MISMATCH type %02x\n", cid, tp, tprop_tnames[surf], e24 & 0x7f); + status &= ~0x100; + } + if (status & 0x200) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s ZETA_STORAGE_TYPE_MISMATCH type %02x\n", cid, tp, tprop_tnames[surf], e24 & 0x7f); + status &= ~0x200; + } + if (status & 0x400) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s RT_STORAGE_TYPE_MISMATCH type %02x\n", cid, tp, tprop_tnames[surf], e24 & 0x7f); + status &= ~0x400; + } + if (status & 0x800) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s DST2D_LINEAR_MISMATCH type %02x\n", cid, tp, tprop_tnames[surf], e24 & 0x7f); + status &= ~0x800; + } + if (status & 0x1000) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s RT_LINEAR_MISMATCH type %02x\n", cid, tp, tprop_tnames[surf], e24 & 0x7f); + status &= ~0x1000; + } + if (status) { + NV_ERROR(dev, "PGRAPH_TRAP_TPROP: ch %d TP %d surf %s status %08x\n", cid, tp, tprop_tnames[surf], status); + } + NV_ERROR(dev, "magic: %08x %08x %08x %08x %08x %08x %08x\n", + e0c, e10, e14, e18, e1c, e20, e24); + nv_wr32(dev, staddr, 0xc0000000); +} + +void nv50_graph_trap_handler(struct drm_device *dev, int cid) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t status = nv_rd32(dev, 0x400108); + uint32_t ustatus; + uint32_t units = nv_rd32(dev, 0x1540); + int i; + + if (status & 0x001) { + ustatus = nv_rd32(dev, 0x400804) & 0x7fffffff; + if (ustatus & 0x00000001) { + nv_wr32(dev, 0x400500, 0); + if (nv_rd32(dev, 0x400808) & 0x80000000) { + uint32_t class = nv_rd32(dev, 0x400814); + uint32_t mthd = nv_rd32(dev, 0x400808) & 0x1ffc; + uint32_t subc = (nv_rd32(dev, 0x400808) >> 16) & 0x7; + uint32_t data = nv_rd32(dev, 0x40080c); + NV_ERROR(dev, "PGRAPH_TRAP_DISPATCH: ch %d sub %d [%04x] mthd %04x data %08x\n", cid, subc, class, mthd, data); + NV_INFO(dev, "PGRAPH_TRAP_DISPATCH: 400808: %08x\n", nv_rd32(dev, 0x400808)); + NV_INFO(dev, "PGRAPH_TRAP_DISPATCH: 400848: %08x\n", nv_rd32(dev, 0x400848)); + nv_wr32(dev, 0x400808, 0); + } else { + NV_ERROR(dev, "PGRAPH_TRAP_DISPATCH: No stuck command?\n"); + } + nv_wr32(dev, 0x4008e8, nv_rd32(dev, 0x4008e8) & 3); + nv_wr32(dev, 0x400848, 0); + } + if (ustatus & 0x00000002) { + /* XXX: this one involves much more pain. */ + NV_ERROR(dev, "PGRAPH_TRAP_QUERY: ch %d.\n", cid); + } + if (ustatus & 0x00000004) { + NV_ERROR(dev, "PGRAPH_TRAP_GRCTX_MMIO: ch %d. This is a kernel bug.\n", cid); + } + if (ustatus & 0x00000008) { + NV_ERROR(dev, "PGRAPH_TRAP_GRCTX_XFER1: ch %d. This is a kernel bug.\n", cid); + } + if (ustatus & 0x00000010) { + NV_ERROR(dev, "PGRAPH_TRAP_GRCTX_XFER2: ch %d. This is a kernel bug.\n", cid); + } + ustatus &= ~0x0000001f; + if (ustatus) + NV_ERROR(dev, "PGRAPH_TRAP_DISPATCH: Unknown ustatus 0x%08x on ch %d\n", ustatus, cid); + nv_wr32(dev, 0x400804, 0xc0000000); + nv_wr32(dev, 0x400108, 0x001); + status &= ~0x001; + } + + if (status & 0x002) { + ustatus = nv_rd32(dev, 0x406800) & 0x7fffffff; + if (ustatus & 1) + NV_ERROR (dev, "PGRAPH_TRAP_M2MF_NOTIFY: ch %d %08x %08x %08x %08x\n", + cid, + nv_rd32(dev, 0x406804), + nv_rd32(dev, 0x406808), + nv_rd32(dev, 0x40680c), + nv_rd32(dev, 0x406810)); + if (ustatus & 2) + NV_ERROR (dev, "PGRAPH_TRAP_M2MF_IN: ch %d %08x %08x %08x %08x\n", + cid, + nv_rd32(dev, 0x406804), + nv_rd32(dev, 0x406808), + nv_rd32(dev, 0x40680c), + nv_rd32(dev, 0x406810)); + if (ustatus & 4) + NV_ERROR (dev, "PGRAPH_TRAP_M2MF_OUT: ch %d %08x %08x %08x %08x\n", + cid, + nv_rd32(dev, 0x406804), + nv_rd32(dev, 0x406808), + nv_rd32(dev, 0x40680c), + nv_rd32(dev, 0x406810)); + ustatus &= ~0x00000007; + if (ustatus) + NV_ERROR(dev, "PGRAPH_TRAP_M2MF: Unknown ustatus 0x%08x on ch %d\n", ustatus, cid); + /* No sane way found yet -- just reset the bugger. */ + nv_wr32(dev, 0x400040, 2); + nv_wr32(dev, 0x400040, 0); + nv_wr32(dev, 0x406800, 0xc0000000); + nv_wr32(dev, 0x400108, 0x002); + status &= ~0x002; + } + + if (status & 0x004) { + ustatus = nv_rd32(dev, 0x400c04) & 0x7fffffff; + if (ustatus & 0x00000001) { + NV_ERROR (dev, "PGRAPH_TRAP_VFETCH: ch %d\n", cid); + } + ustatus &= ~0x00000001; + if (ustatus) + NV_ERROR(dev, "PGRAPH_TRAP_VFETCH: Unknown ustatus 0x%08x on ch %d\n", ustatus, cid); + nv_wr32(dev, 0x400c04, 0xc0000000); + nv_wr32(dev, 0x400108, 0x004); + status &= ~0x004; + } + + if (status & 0x008) { + ustatus = nv_rd32(dev, 0x401800) & 0x7fffffff; + if (ustatus & 0x00000001) { + NV_ERROR (dev, "PGRAPH_TRAP_STRMOUT: ch %d %08x %08x %08x %08x\n", cid, + nv_rd32(dev, 0x401804), + nv_rd32(dev, 0x401808), + nv_rd32(dev, 0x40180c), + nv_rd32(dev, 0x401810)); + } + ustatus &= ~0x00000001; + if (ustatus) + NV_ERROR(dev, "PGRAPH_TRAP_STRMOUT: Unknown ustatus 0x%08x on ch %d\n", ustatus, cid); + /* No sane way found yet -- just reset the bugger. */ + nv_wr32(dev, 0x400040, 0x80); + nv_wr32(dev, 0x400040, 0); + nv_wr32(dev, 0x401800, 0xc0000000); + nv_wr32(dev, 0x400108, 0x008); + status &= ~0x008; + } + + if (status & 0x010) { + ustatus = nv_rd32(dev, 0x405018) & 0x7fffffff; + if (ustatus & 0x00000001) { + NV_ERROR (dev, "PGRAPH_TRAP_CCACHE: ch %d\n", cid); + } + ustatus &= ~0x00000001; + if (ustatus) + NV_ERROR(dev, "PGRAPH_TRAP_CCACHE: Unknown ustatus 0x%08x on ch %d\n", ustatus, cid); + nv_wr32(dev, 0x405018, 0xc0000000); + nv_wr32(dev, 0x400108, 0x010); + status &= ~0x010; + } + + if (status & 0x020) { + ustatus = nv_rd32(dev, 0x402000) & 0x7fffffff; + if (ustatus & 0x00000001) { + NV_ERROR (dev, "PGRAPH_TRAP_CLIPID: ch %d\n", cid); + } + ustatus &= ~0x00000001; + if (ustatus) + NV_ERROR(dev, "PGRAPH_TRAP_CLIPID: Unknown ustatus 0x%08x on ch %d\n", ustatus, cid); + nv_wr32(dev, 0x402000, 0xc0000000); + nv_wr32(dev, 0x400108, 0x020); + status &= ~0x020; + } + + if (status & 0x040) { + for (i = 0; i < 16; i++) + if (units & 1 << i) { + if (dev_priv->chipset < 0xa0) + ustatus = nv_rd32(dev, 0x408900 + i * 0x1000); + else + ustatus = nv_rd32(dev, 0x408600 + i * 0x800); + if (ustatus & 0x7fffffff) + nv50_graph_tex_trap(dev, cid, i); + } + nv_wr32(dev, 0x400108, 0x040); + status &= ~0x040; + } + + if (status & 0x080) { + for (i = 0; i < 16; i++) + if (units & 1 << i) { + if (dev_priv->chipset < 0xa0) + ustatus = nv_rd32(dev, 0x408314 + i * 0x1000); + else + ustatus = nv_rd32(dev, 0x40831c + i * 0x800); + if (ustatus & 0x7fffffff) + nv50_graph_mpc_trap(dev, cid, i); + } + nv_wr32(dev, 0x400108, 0x080); + status &= ~0x080; + } + + if (status & 0x100) { + for (i = 0; i < 16; i++) + if (units & 1 << i) { + if (dev_priv->chipset < 0xa0) + ustatus = nv_rd32(dev, 0x408e08 + i * 0x1000); + else + ustatus = nv_rd32(dev, 0x408708 + i * 0x800); + if (ustatus & 0x7fffffff) + nv50_graph_tprop_trap(dev, cid, i); + } + nv_wr32(dev, 0x400108, 0x100); + status &= ~0x100; + } + + /* XXX: per-TP traps. */ + + if (status) { + NV_ERROR(dev, "Unknown PGRAPH trap %08x on ch %d\n", status, cid); + nv_wr32(dev, 0x400108, status); + } +} + +void nv50_graph_irq_handler(struct drm_device *dev, int irq) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv50_graph_engine *graph = nv50_graph(dev_priv->engines[PSCNV_ENGINE_GRAPH]); + uint32_t status; + unsigned long flags; + uint32_t st, chandle, addr, data, datah, ecode, class, subc, mthd; + int cid; + spin_lock_irqsave(&graph->lock, flags); + status = nv_rd32(dev, 0x400100); + ecode = nv_rd32(dev, 0x400110); + st = nv_rd32(dev, 0x400700); + addr = nv_rd32(dev, 0x400704); + mthd = addr & 0x1ffc; + subc = (addr >> 16) & 7; + data = nv_rd32(dev, 0x400708); + datah = nv_rd32(dev, 0x40070c); + chandle = nv_rd32(dev, 0x400784); + class = nv_rd32(dev, 0x400814) & 0xffff; + cid = pscnv_chan_handle_lookup(dev, chandle); + if (cid == 128) { + NV_ERROR(dev, "PGRAPH: UNKNOWN channel %x active!\n", chandle); + } + + if (status & 0x00000001) { + NV_ERROR(dev, "PGRAPH_NOTIFY: ch %d\n", cid); + nv_wr32(dev, 0x400100, 0x00000001); + status &= ~0x00000001; + } + if (status & 0x00000002) { + NV_ERROR(dev, "PGRAPH_QUERY: ch %d\n", cid); + nv_wr32(dev, 0x400100, 0x00000002); + status &= ~0x00000002; + } + if (status & 0x00000004) { + NV_ERROR(dev, "PGRAPH_SYNC: ch %d\n", cid); + nv_wr32(dev, 0x400100, 0x00000004); + status &= ~0x00000004; + } + if (status & 0x00000010) { + NV_ERROR(dev, "PGRAPH_ILLEGAL_MTHD: ch %d sub %d [%04x] mthd %04x data %08x\n", cid, subc, class, mthd, data); + nv_wr32(dev, 0x400100, 0x00000010); + status &= ~0x00000010; + } + if (status & 0x00000020) { + NV_ERROR(dev, "PGRAPH_ILLEGAL_CLASS: ch %d sub %d [%04x] mthd %04x data %08x\n", cid, subc, class, mthd, data); + nv_wr32(dev, 0x400100, 0x00000020); + status &= ~0x00000020; + } + if (status & 0x00000040) { + NV_ERROR(dev, "PGRAPH_DOUBLE_NOTIFY: ch %d sub %d [%04x] mthd %04x data %08x\n", cid, subc, class, mthd, data); + nv_wr32(dev, 0x400100, 0x00000040); + status &= ~0x00000040; + } + if (status & 0x00010000) { + NV_ERROR(dev, "PGRAPH_BUFFER_NOTIFY: ch %d\n", cid); + nv_wr32(dev, 0x400100, 0x00010000); + status &= ~0x00010000; + } + if (status & 0x00100000) { + struct pscnv_enumval *ev; + ev = pscnv_enum_find(dispatch_errors, ecode); + if (ev) + NV_ERROR(dev, "PGRAPH_DISPATCH_ERROR [%s]: ch %d sub %d [%04x] mthd %04x data %08x\n", ev->name, cid, subc, class, mthd, data); + else { + uint32_t base = (dev_priv->chipset > 0xa0 && dev_priv->chipset < 0xaa ? 0x404800 : 0x405400); + int i; + NV_ERROR(dev, "PGRAPH_DISPATCH_ERROR [%x]: ch %d sub %d [%04x] mthd %04x data %08x\n", ecode, cid, subc, class, mthd, data); + for (i = 0; i < 0x400; i += 4) + NV_ERROR(dev, "DD %06x: %08x\n", base + i, nv_rd32(dev, base + i)); + } + nv_wr32(dev, 0x400100, 0x00100000); + status &= ~0x00100000; + } + + if (status & 0x00200000) { + nv50_graph_trap_handler(dev, cid); + nv_wr32(dev, 0x400100, 0x00200000); + status &= ~0x00200000; + } + + if (status & 0x01000000) { + addr = nv_rd32(dev, 0x400808); + subc = addr >> 16 & 7; + mthd = addr & 0x1ffc; + data = nv_rd32(dev, 0x40080c); + NV_ERROR(dev, "PGRAPH_SINGLE_STEP: ch %d sub %d [%04x] mthd %04x data %08x\n", cid, subc, class, mthd, data); + nv_wr32(dev, 0x400100, 0x01000000); + status &= ~0x01000000; + } + + if (status) { + NV_ERROR(dev, "Unknown PGRAPH interrupt %08x\n", status); + NV_ERROR(dev, "PGRAPH: st %d ch %d sub %d [%04x] mthd %04x data %08x%08x\n", + st, cid, subc, class, mthd, datah, data); + nv_wr32(dev, 0x400100, status); + } + nv50_vm_trap(dev); + nv_wr32(dev, 0x400500, 0x10001); + spin_unlock_irqrestore(&graph->lock, flags); +} diff --git a/driver/pscnv/nv50_grctx.c b/driver/pscnv/nv50_grctx.c new file mode 100644 index 00000000..efa7ef5f --- /dev/null +++ b/driver/pscnv/nv50_grctx.c @@ -0,0 +1,3337 @@ +/* + * Copyright 2009 Marcin KoÅ›cielnicki + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#define CP_FLAG_CLEAR 0 +#define CP_FLAG_SET 1 +#define CP_FLAG_SWAP_DIRECTION ((0 * 32) + 0) +#define CP_FLAG_SWAP_DIRECTION_LOAD 0 +#define CP_FLAG_SWAP_DIRECTION_SAVE 1 +#define CP_FLAG_UNK01 ((0 * 32) + 1) +#define CP_FLAG_UNK01_CLEAR 0 +#define CP_FLAG_UNK01_SET 1 +#define CP_FLAG_UNK03 ((0 * 32) + 3) +#define CP_FLAG_UNK03_CLEAR 0 +#define CP_FLAG_UNK03_SET 1 +#define CP_FLAG_USER_SAVE ((0 * 32) + 5) +#define CP_FLAG_USER_SAVE_NOT_PENDING 0 +#define CP_FLAG_USER_SAVE_PENDING 1 +#define CP_FLAG_USER_LOAD ((0 * 32) + 6) +#define CP_FLAG_USER_LOAD_NOT_PENDING 0 +#define CP_FLAG_USER_LOAD_PENDING 1 +#define CP_FLAG_UNK0B ((0 * 32) + 0xb) +#define CP_FLAG_UNK0B_CLEAR 0 +#define CP_FLAG_UNK0B_SET 1 +#define CP_FLAG_UNK1D ((0 * 32) + 0x1d) +#define CP_FLAG_UNK1D_CLEAR 0 +#define CP_FLAG_UNK1D_SET 1 +#define CP_FLAG_SYNC_ACK ((0 * 32) + 0x1f) +#define CP_FLAG_SYNC_ACK_FALSE 0 +#define CP_FLAG_SYNC_ACK_TRUE 1 +#define CP_FLAG_UNK20 ((1 * 32) + 0) +#define CP_FLAG_UNK20_CLEAR 0 +#define CP_FLAG_UNK20_SET 1 +#define CP_FLAG_STATUS ((2 * 32) + 0) +#define CP_FLAG_STATUS_BUSY 0 +#define CP_FLAG_STATUS_IDLE 1 +#define CP_FLAG_AUTO_SAVE ((2 * 32) + 4) +#define CP_FLAG_AUTO_SAVE_NOT_PENDING 0 +#define CP_FLAG_AUTO_SAVE_PENDING 1 +#define CP_FLAG_AUTO_LOAD ((2 * 32) + 5) +#define CP_FLAG_AUTO_LOAD_NOT_PENDING 0 +#define CP_FLAG_AUTO_LOAD_PENDING 1 +#define CP_FLAG_NEWCTX ((2 * 32) + 10) +#define CP_FLAG_NEWCTX_BUSY 0 +#define CP_FLAG_NEWCTX_DONE 1 +#define CP_FLAG_XFER ((2 * 32) + 11) +#define CP_FLAG_XFER_IDLE 0 +#define CP_FLAG_XFER_BUSY 1 +#define CP_FLAG_ALWAYS ((2 * 32) + 13) +#define CP_FLAG_ALWAYS_FALSE 0 +#define CP_FLAG_ALWAYS_TRUE 1 +#define CP_FLAG_INTR ((2 * 32) + 15) +#define CP_FLAG_INTR_NOT_PENDING 0 +#define CP_FLAG_INTR_PENDING 1 +#define CP_FLAG_SYNC_REQ ((3 * 32) + 0) +#define CP_FLAG_SYNC_REQ_FALSE 0 +#define CP_FLAG_SYNC_REQ_TRUE 1 + +#define CP_CTX 0x00100000 +#define CP_CTX_COUNT 0x000f0000 +#define CP_CTX_COUNT_SHIFT 16 +#define CP_CTX_REG 0x00003fff +#define CP_LOAD_SR 0x00200000 +#define CP_LOAD_SR_VALUE 0x000fffff +#define CP_BRA 0x00400000 +#define CP_BRA_IP 0x0001ff00 +#define CP_BRA_IP_SHIFT 8 +#define CP_BRA_IF_CLEAR 0x00000080 +#define CP_BRA_FLAG 0x0000007f +#define CP_WAIT 0x00500000 +#define CP_WAIT_SET 0x00000080 +#define CP_WAIT_FLAG 0x0000007f +#define CP_SET 0x00700000 +#define CP_SET_1 0x00000080 +#define CP_SET_FLAG 0x0000007f +#define CP_NEWCTX 0x00600004 +#define CP_NEXT_TO_SWAP 0x00600005 +#define CP_SET_CONTEXT_POINTER 0x00600006 +#define CP_SET_XFER_POINTER 0x00600007 +#define CP_ENABLE 0x00600009 +#define CP_END 0x0060000c +#define CP_NEXT_TO_CURRENT 0x0060000d +#define CP_DISABLE1 0x0090ffff +#define CP_DISABLE2 0x0091ffff +#define CP_XFER_1 0x008000ff +#define CP_XFER_2 0x008800ff +#define CP_SEEK_1 0x00c000ff +#define CP_SEEK_2 0x00c800ff + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_grctx.h" + +#define IS_NVA3F(x) (((x) > 0xa0 && (x) < 0xaa) || (x) == 0xaf) +#define IS_NVAAF(x) ((x) >= 0xaa && (x) <= 0xac) + +/* + * This code deals with PGRAPH contexts on NV50 family cards. Like NV40, it's + * the GPU itself that does context-switching, but it needs a special + * microcode to do it. And it's the driver's task to supply this microcode, + * further known as ctxprog, as well as the initial context values, known + * as ctxvals. + * + * Without ctxprog, you cannot switch contexts. Not even in software, since + * the majority of context [xfer strands] isn't accessible directly. You're + * stuck with a single channel, and you also suffer all the problems resulting + * from missing ctxvals, since you cannot load them. + * + * Without ctxvals, you're stuck with PGRAPH's default context. It's enough to + * run 2d operations, but trying to utilise 3d or CUDA will just lock you up, + * since you don't have... some sort of needed setup. + * + * Nouveau will just disable acceleration if not given ctxprog + ctxvals, since + * it's too much hassle to handle no-ctxprog as a special case. + */ + +/* + * How ctxprogs work. + * + * The ctxprog is written in its own kind of microcode, with very small and + * crappy set of available commands. You upload it to a small [512 insns] + * area of memory on PGRAPH, and it'll be run when PFIFO wants PGRAPH to + * switch channel. or when the driver explicitely requests it. Stuff visible + * to ctxprog consists of: PGRAPH MMIO registers, PGRAPH context strands, + * the per-channel context save area in VRAM [known as ctxvals or grctx], + * 4 flags registers, a scratch register, two grctx pointers, plus many + * random poorly-understood details. + * + * When ctxprog runs, it's supposed to check what operations are asked of it, + * save old context if requested, optionally reset PGRAPH and switch to the + * new channel, and load the new context. Context consists of three major + * parts: subset of MMIO registers and two "xfer areas". + */ + +/* TODO: + * - document unimplemented bits compared to nvidia + * - NVAx: make a TP subroutine, use it. + * - use 0x4008fc instead of 0x1540? + */ + +enum cp_label { + cp_check_load = 1, + cp_setup_auto_load, + cp_setup_load, + cp_setup_save, + cp_swap_state, + cp_prepare_exit, + cp_exit, + cp_sync, +}; + +static void nv50_graph_construct_mmio(struct nouveau_grctx *ctx); +static void nv50_graph_construct_xfer1(struct nouveau_grctx *ctx); +static void nv50_graph_construct_xfer2(struct nouveau_grctx *ctx); + +/* Main function: construct the ctxprog skeleton, call the other functions. */ + +int +nv50_grctx_init(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + + switch (dev_priv->chipset) { + case 0x50: + case 0x84: + case 0x86: + case 0x92: + case 0x94: + case 0x96: + case 0x98: + case 0xa0: + case 0xa3: + case 0xa5: + case 0xa8: + case 0xaa: + case 0xac: + case 0xaf: + break; + default: + NV_ERROR(ctx->dev, "I don't know how to make a ctxprog for " + "your NV%x card.\n", dev_priv->chipset); + NV_ERROR(ctx->dev, "Disabling acceleration. Please contact " + "the devs.\n"); + return -ENOSYS; + } + /* decide whether we're loading/unloading the context */ + cp_bra (ctx, AUTO_SAVE, PENDING, cp_setup_save); + cp_bra (ctx, USER_SAVE, PENDING, cp_setup_save); + + cp_name(ctx, cp_check_load); + cp_bra (ctx, AUTO_LOAD, PENDING, cp_setup_auto_load); + cp_bra (ctx, USER_LOAD, PENDING, cp_setup_load); + cp_bra (ctx, ALWAYS, TRUE, cp_exit); + + /* setup for context load */ + cp_name(ctx, cp_setup_auto_load); + cp_out (ctx, CP_DISABLE1); + cp_out (ctx, CP_DISABLE2); + cp_out (ctx, CP_ENABLE); + cp_out (ctx, CP_NEXT_TO_SWAP); + cp_set (ctx, UNK01, SET); + cp_name(ctx, cp_setup_load); + cp_out (ctx, CP_NEWCTX); + cp_wait(ctx, NEWCTX, BUSY); + cp_set (ctx, UNK1D, CLEAR); + cp_set (ctx, SWAP_DIRECTION, LOAD); + cp_bra (ctx, UNK0B, SET, cp_prepare_exit); + cp_bra (ctx, ALWAYS, TRUE, cp_swap_state); + + cp_name(ctx, cp_sync); + cp_set (ctx, SYNC_ACK, TRUE); + cp_bra (ctx, SYNC_REQ, TRUE, cp_sync); + cp_set (ctx, SYNC_ACK, FALSE); + cp_bra (ctx, SYNC_REQ, TRUE, cp_sync); + + /* setup for context save */ + cp_name(ctx, cp_setup_save); + cp_set (ctx, UNK1D, SET); + cp_bra (ctx, SYNC_REQ, TRUE, cp_sync); + cp_bra (ctx, INTR, PENDING, cp_setup_save); + cp_bra (ctx, STATUS, BUSY, cp_setup_save); + cp_set (ctx, UNK01, SET); + cp_set (ctx, SWAP_DIRECTION, SAVE); + + /* general PGRAPH state */ + cp_name(ctx, cp_swap_state); + cp_set (ctx, UNK03, SET); + cp_pos (ctx, 0x00004/4); + cp_ctx (ctx, 0x400828, 1); /* needed. otherwise, flickering happens. */ + cp_pos (ctx, 0x00100/4); + nv50_graph_construct_mmio(ctx); + nv50_graph_construct_xfer1(ctx); + nv50_graph_construct_xfer2(ctx); + + cp_bra (ctx, SWAP_DIRECTION, SAVE, cp_check_load); + + cp_set (ctx, UNK20, SET); + cp_set (ctx, SWAP_DIRECTION, SAVE); /* no idea why this is needed, but fixes at least one lockup. */ + cp_lsr (ctx, ctx->ctxvals_base); + cp_out (ctx, CP_SET_XFER_POINTER); + cp_lsr (ctx, 4); + cp_out (ctx, CP_SEEK_1); + cp_out (ctx, CP_XFER_1); + cp_wait(ctx, XFER, BUSY); + + /* pre-exit state updates */ + cp_name(ctx, cp_prepare_exit); + cp_set (ctx, UNK01, CLEAR); + cp_set (ctx, UNK03, CLEAR); + cp_set (ctx, UNK1D, CLEAR); + + cp_bra (ctx, USER_SAVE, PENDING, cp_exit); + cp_out (ctx, CP_NEXT_TO_CURRENT); + + cp_name(ctx, cp_exit); + cp_set (ctx, USER_SAVE, NOT_PENDING); + cp_set (ctx, USER_LOAD, NOT_PENDING); + cp_out (ctx, CP_END); + ctx->ctxvals_pos += 0x400; /* padding... no idea why you need it */ + + return 0; +} + +/* + * Constructs MMIO part of ctxprog and ctxvals. Just a matter of knowing which + * registers to save/restore and the default values for them. + */ + +static void +nv50_graph_construct_mmio_ddata(struct nouveau_grctx *ctx); + +static void +nv50_graph_construct_mmio(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int i, j; + int offset, base; + uint32_t units = nv_rd32 (ctx->dev, 0x1540); + + /* 0800: DISPATCH */ + cp_ctx(ctx, 0x400808, 7); + gr_def(ctx, 0x400814, 0x00000030); + cp_ctx(ctx, 0x400834, 0x32); + if (dev_priv->chipset == 0x50) { + gr_def(ctx, 0x400834, 0xff400040); + gr_def(ctx, 0x400838, 0xfff00080); + gr_def(ctx, 0x40083c, 0xfff70090); + gr_def(ctx, 0x400840, 0xffe806a8); + } + gr_def(ctx, 0x400844, 0x00000002); + if (IS_NVA3F(dev_priv->chipset)) + gr_def(ctx, 0x400894, 0x00001000); + gr_def(ctx, 0x4008e8, 0x00000003); + gr_def(ctx, 0x4008ec, 0x00001000); + if (dev_priv->chipset == 0x50) + cp_ctx(ctx, 0x400908, 0xb); + else if (dev_priv->chipset < 0xa0) + cp_ctx(ctx, 0x400908, 0xc); + else + cp_ctx(ctx, 0x400908, 0xe); + + if (dev_priv->chipset >= 0xa0) + cp_ctx(ctx, 0x400b00, 0x1); + if (IS_NVA3F(dev_priv->chipset)) { + cp_ctx(ctx, 0x400b10, 0x1); + gr_def(ctx, 0x400b10, 0x0001629d); + cp_ctx(ctx, 0x400b20, 0x1); + gr_def(ctx, 0x400b20, 0x0001629d); + } + + nv50_graph_construct_mmio_ddata(ctx); + + /* 0C00: VFETCH */ + cp_ctx(ctx, 0x400c08, 0x2); + gr_def(ctx, 0x400c08, 0x0000fe0c); + + /* 1000 */ + if (dev_priv->chipset < 0xa0) { + cp_ctx(ctx, 0x401008, 0x4); + gr_def(ctx, 0x401014, 0x00001000); + } else if (!IS_NVA3F(dev_priv->chipset)) { + cp_ctx(ctx, 0x401008, 0x5); + gr_def(ctx, 0x401018, 0x00001000); + } else { + cp_ctx(ctx, 0x401008, 0x5); + gr_def(ctx, 0x401018, 0x00004000); + } + + /* 1400 */ + cp_ctx(ctx, 0x401400, 0x8); + cp_ctx(ctx, 0x401424, 0x3); + if (dev_priv->chipset == 0x50) + gr_def(ctx, 0x40142c, 0x0001fd87); + else + gr_def(ctx, 0x40142c, 0x00000187); + cp_ctx(ctx, 0x401540, 0x5); + gr_def(ctx, 0x401550, 0x00001018); + + /* 1800: STREAMOUT */ + cp_ctx(ctx, 0x401814, 0x1); + gr_def(ctx, 0x401814, 0x000000ff); + if (dev_priv->chipset == 0x50) { + cp_ctx(ctx, 0x40181c, 0xe); + gr_def(ctx, 0x401850, 0x00000004); + } else if (dev_priv->chipset < 0xa0) { + cp_ctx(ctx, 0x40181c, 0xf); + gr_def(ctx, 0x401854, 0x00000004); + } else { + cp_ctx(ctx, 0x40181c, 0x13); + gr_def(ctx, 0x401864, 0x00000004); + } + + /* 1C00 */ + cp_ctx(ctx, 0x401c00, 0x1); + switch (dev_priv->chipset) { + case 0x50: + gr_def(ctx, 0x401c00, 0x0001005f); + break; + case 0x84: + case 0x86: + case 0x94: + gr_def(ctx, 0x401c00, 0x044d00df); + break; + case 0x92: + case 0x96: + case 0x98: + case 0xa0: + case 0xaa: + case 0xac: + gr_def(ctx, 0x401c00, 0x042500df); + break; + case 0xa3: + case 0xa5: + case 0xa8: + case 0xaf: + gr_def(ctx, 0x401c00, 0x142500df); + break; + } + + /* 2000 */ + + /* 2400 */ + cp_ctx(ctx, 0x402400, 0x1); + if (dev_priv->chipset == 0x50) + cp_ctx(ctx, 0x402408, 0x1); + else + cp_ctx(ctx, 0x402408, 0x2); + gr_def(ctx, 0x402408, 0x00000600); + + /* 2800: CSCHED */ + cp_ctx(ctx, 0x402800, 0x1); + if (dev_priv->chipset == 0x50) + gr_def(ctx, 0x402800, 0x00000006); + + /* 2C00: ZCULL */ + cp_ctx(ctx, 0x402c08, 0x6); + if (dev_priv->chipset != 0x50) + gr_def(ctx, 0x402c14, 0x01000000); + gr_def(ctx, 0x402c18, 0x000000ff); + if (dev_priv->chipset == 0x50) + cp_ctx(ctx, 0x402ca0, 0x1); + else + cp_ctx(ctx, 0x402ca0, 0x2); + if (dev_priv->chipset < 0xa0) + gr_def(ctx, 0x402ca0, 0x00000400); + else if (!IS_NVA3F(dev_priv->chipset)) + gr_def(ctx, 0x402ca0, 0x00000800); + else + gr_def(ctx, 0x402ca0, 0x00000400); + cp_ctx(ctx, 0x402cac, 0x4); + + /* 3000: ENG2D */ + cp_ctx(ctx, 0x403004, 0x1); + gr_def(ctx, 0x403004, 0x00000001); + + /* 3400 */ + if (dev_priv->chipset >= 0xa0) { + cp_ctx(ctx, 0x403404, 0x1); + gr_def(ctx, 0x403404, 0x00000001); + } + + /* 5000: CCACHE */ + cp_ctx(ctx, 0x405000, 0x1); + switch (dev_priv->chipset) { + case 0x50: + gr_def(ctx, 0x405000, 0x00300080); + break; + case 0x84: + case 0xa0: + case 0xa3: + case 0xa5: + case 0xa8: + case 0xaa: + case 0xac: + case 0xaf: + gr_def(ctx, 0x405000, 0x000e0080); + break; + case 0x86: + case 0x92: + case 0x94: + case 0x96: + case 0x98: + gr_def(ctx, 0x405000, 0x00000080); + break; + } + cp_ctx(ctx, 0x405014, 0x1); + gr_def(ctx, 0x405014, 0x00000004); + cp_ctx(ctx, 0x40501c, 0x1); + cp_ctx(ctx, 0x405024, 0x1); + cp_ctx(ctx, 0x40502c, 0x1); + + /* 6000? */ + if (dev_priv->chipset == 0x50) + cp_ctx(ctx, 0x4063e0, 0x1); + + /* 6800: M2MF */ + if (dev_priv->chipset < 0x90) { + cp_ctx(ctx, 0x406814, 0x2b); + gr_def(ctx, 0x406818, 0x00000f80); + gr_def(ctx, 0x406860, 0x007f0080); + gr_def(ctx, 0x40689c, 0x007f0080); + } else { + cp_ctx(ctx, 0x406814, 0x4); + if (dev_priv->chipset == 0x98) + gr_def(ctx, 0x406818, 0x00000f80); + else + gr_def(ctx, 0x406818, 0x00001f80); + if (IS_NVA3F(dev_priv->chipset)) + gr_def(ctx, 0x40681c, 0x00000030); + cp_ctx(ctx, 0x406830, 0x3); + } + + /* 7000: per-ROP group state */ + for (i = 0; i < 8; i++) { + if (units & (1<<(i+16))) { + cp_ctx(ctx, 0x407000 + (i<<8), 3); + if (dev_priv->chipset == 0x50) + gr_def(ctx, 0x407000 + (i<<8), 0x1b74f820); + else if (dev_priv->chipset != 0xa5) + gr_def(ctx, 0x407000 + (i<<8), 0x3b74f821); + else + gr_def(ctx, 0x407000 + (i<<8), 0x7b74f821); + gr_def(ctx, 0x407004 + (i<<8), 0x89058001); + + if (dev_priv->chipset == 0x50) { + cp_ctx(ctx, 0x407010 + (i<<8), 1); + } else if (dev_priv->chipset < 0xa0) { + cp_ctx(ctx, 0x407010 + (i<<8), 2); + gr_def(ctx, 0x407010 + (i<<8), 0x00001000); + gr_def(ctx, 0x407014 + (i<<8), 0x0000001f); + } else { + cp_ctx(ctx, 0x407010 + (i<<8), 3); + gr_def(ctx, 0x407010 + (i<<8), 0x00001000); + if (dev_priv->chipset != 0xa5) + gr_def(ctx, 0x407014 + (i<<8), 0x000000ff); + else + gr_def(ctx, 0x407014 + (i<<8), 0x000001ff); + } + + cp_ctx(ctx, 0x407080 + (i<<8), 4); + if (dev_priv->chipset != 0xa5) + gr_def(ctx, 0x407080 + (i<<8), 0x027c10fa); + else + gr_def(ctx, 0x407080 + (i<<8), 0x827c10fa); + if (dev_priv->chipset == 0x50) + gr_def(ctx, 0x407084 + (i<<8), 0x000000c0); + else + gr_def(ctx, 0x407084 + (i<<8), 0x400000c0); + gr_def(ctx, 0x407088 + (i<<8), 0xb7892080); + + if (dev_priv->chipset < 0xa0) + cp_ctx(ctx, 0x407094 + (i<<8), 1); + else if (!IS_NVA3F(dev_priv->chipset)) + cp_ctx(ctx, 0x407094 + (i<<8), 3); + else { + cp_ctx(ctx, 0x407094 + (i<<8), 4); + gr_def(ctx, 0x4070a0 + (i<<8), 1); + } + } + } + + cp_ctx(ctx, 0x407c00, 0x3); + if (dev_priv->chipset < 0x90) + gr_def(ctx, 0x407c00, 0x00010040); + else if (dev_priv->chipset < 0xa0) + gr_def(ctx, 0x407c00, 0x00390040); + else + gr_def(ctx, 0x407c00, 0x003d0040); + gr_def(ctx, 0x407c08, 0x00000022); + if (dev_priv->chipset >= 0xa0) { + cp_ctx(ctx, 0x407c10, 0x3); + cp_ctx(ctx, 0x407c20, 0x1); + cp_ctx(ctx, 0x407c2c, 0x1); + } + + if (dev_priv->chipset < 0xa0) { + cp_ctx(ctx, 0x407d00, 0x9); + } else { + cp_ctx(ctx, 0x407d00, 0x15); + } + if (dev_priv->chipset == 0x98) + gr_def(ctx, 0x407d08, 0x00380040); + else { + if (dev_priv->chipset < 0x90) + gr_def(ctx, 0x407d08, 0x00010040); + else if (dev_priv->chipset < 0xa0) + gr_def(ctx, 0x407d08, 0x00390040); + else + gr_def(ctx, 0x407d08, 0x003d0040); + gr_def(ctx, 0x407d0c, 0x00000022); + } + + /* 8000+: per-TP state */ + for (i = 0; i < 10; i++) { + if (units & (1<chipset < 0xa0) + base = 0x408000 + (i<<12); + else + base = 0x408000 + (i<<11); + if (dev_priv->chipset < 0xa0) + offset = base + 0xc00; + else + offset = base + 0x80; + cp_ctx(ctx, offset + 0x00, 1); + gr_def(ctx, offset + 0x00, 0x0000ff0a); + cp_ctx(ctx, offset + 0x08, 1); + + /* per-MP state */ + for (j = 0; j < (dev_priv->chipset < 0xa0 ? 2 : 4); j++) { + if (!(units & (1 << (j+24)))) continue; + if (dev_priv->chipset < 0xa0) + offset = base + 0x200 + (j<<7); + else + offset = base + 0x100 + (j<<7); + cp_ctx(ctx, offset, 0x20); + gr_def(ctx, offset + 0x00, 0x01800000); + gr_def(ctx, offset + 0x04, 0x00160000); + gr_def(ctx, offset + 0x08, 0x01800000); + gr_def(ctx, offset + 0x18, 0x0003ffff); + switch (dev_priv->chipset) { + case 0x50: + gr_def(ctx, offset + 0x1c, 0x00080000); + break; + case 0x84: + gr_def(ctx, offset + 0x1c, 0x00880000); + break; + case 0x86: + gr_def(ctx, offset + 0x1c, 0x008c0000); + break; + case 0x92: + case 0x96: + case 0x98: + gr_def(ctx, offset + 0x1c, 0x118c0000); + break; + case 0x94: + gr_def(ctx, offset + 0x1c, 0x10880000); + break; + case 0xa0: + case 0xa5: + gr_def(ctx, offset + 0x1c, 0x310c0000); + break; + case 0xa3: + case 0xa8: + case 0xaa: + case 0xac: + case 0xaf: + gr_def(ctx, offset + 0x1c, 0x300c0000); + break; + } + gr_def(ctx, offset + 0x40, 0x00010401); + if (dev_priv->chipset == 0x50) + gr_def(ctx, offset + 0x48, 0x00000040); + else + gr_def(ctx, offset + 0x48, 0x00000078); + gr_def(ctx, offset + 0x50, 0x000000bf); + gr_def(ctx, offset + 0x58, 0x00001210); + if (dev_priv->chipset == 0x50) + gr_def(ctx, offset + 0x5c, 0x00000080); + else + gr_def(ctx, offset + 0x5c, 0x08000080); + if (dev_priv->chipset >= 0xa0) + gr_def(ctx, offset + 0x68, 0x0000003e); + } + + if (dev_priv->chipset < 0xa0) + cp_ctx(ctx, base + 0x300, 0x4); + else + cp_ctx(ctx, base + 0x300, 0x5); + if (dev_priv->chipset == 0x50) + gr_def(ctx, base + 0x304, 0x00007070); + else if (dev_priv->chipset < 0xa0) + gr_def(ctx, base + 0x304, 0x00027070); + else if (!IS_NVA3F(dev_priv->chipset)) + gr_def(ctx, base + 0x304, 0x01127070); + else + gr_def(ctx, base + 0x304, 0x05127070); + + if (dev_priv->chipset < 0xa0) + cp_ctx(ctx, base + 0x318, 1); + else + cp_ctx(ctx, base + 0x320, 1); + if (dev_priv->chipset == 0x50) + gr_def(ctx, base + 0x318, 0x0003ffff); + else if (dev_priv->chipset < 0xa0) + gr_def(ctx, base + 0x318, 0x03ffffff); + else + gr_def(ctx, base + 0x320, 0x07ffffff); + + if (dev_priv->chipset < 0xa0) + cp_ctx(ctx, base + 0x324, 5); + else + cp_ctx(ctx, base + 0x328, 4); + + if (dev_priv->chipset < 0xa0) { + cp_ctx(ctx, base + 0x340, 9); + offset = base + 0x340; + } else if (!IS_NVA3F(dev_priv->chipset)) { + cp_ctx(ctx, base + 0x33c, 0xb); + offset = base + 0x344; + } else { + cp_ctx(ctx, base + 0x33c, 0xd); + offset = base + 0x344; + } + gr_def(ctx, offset + 0x0, 0x00120407); + gr_def(ctx, offset + 0x4, 0x05091507); + if (dev_priv->chipset == 0x84) + gr_def(ctx, offset + 0x8, 0x05100202); + else + gr_def(ctx, offset + 0x8, 0x05010202); + gr_def(ctx, offset + 0xc, 0x00030201); + if (dev_priv->chipset == 0xa3) + cp_ctx(ctx, base + 0x36c, 1); + + cp_ctx(ctx, base + 0x400, 2); + gr_def(ctx, base + 0x404, 0x00000040); + cp_ctx(ctx, base + 0x40c, 2); + gr_def(ctx, base + 0x40c, 0x0d0c0b0a); + gr_def(ctx, base + 0x410, 0x00141210); + + if (dev_priv->chipset < 0xa0) + offset = base + 0x800; + else + offset = base + 0x500; + cp_ctx(ctx, offset, 6); + gr_def(ctx, offset + 0x0, 0x000001f0); + gr_def(ctx, offset + 0x4, 0x00000001); + gr_def(ctx, offset + 0x8, 0x00000003); + if (dev_priv->chipset == 0x50 || IS_NVAAF(dev_priv->chipset)) + gr_def(ctx, offset + 0xc, 0x00008000); + gr_def(ctx, offset + 0x14, 0x00039e00); + cp_ctx(ctx, offset + 0x1c, 2); + if (dev_priv->chipset == 0x50) + gr_def(ctx, offset + 0x1c, 0x00000040); + else + gr_def(ctx, offset + 0x1c, 0x00000100); + gr_def(ctx, offset + 0x20, 0x00003800); + + if (dev_priv->chipset >= 0xa0) { + cp_ctx(ctx, base + 0x54c, 2); + if (!IS_NVA3F(dev_priv->chipset)) + gr_def(ctx, base + 0x54c, 0x003fe006); + else + gr_def(ctx, base + 0x54c, 0x003fe007); + gr_def(ctx, base + 0x550, 0x003fe000); + } + + if (dev_priv->chipset < 0xa0) + offset = base + 0xa00; + else + offset = base + 0x680; + cp_ctx(ctx, offset, 1); + gr_def(ctx, offset, 0x00404040); + + if (dev_priv->chipset < 0xa0) + offset = base + 0xe00; + else + offset = base + 0x700; + cp_ctx(ctx, offset, 2); + if (dev_priv->chipset < 0xa0) + gr_def(ctx, offset, 0x0077f005); + else if (dev_priv->chipset == 0xa5) + gr_def(ctx, offset, 0x6cf7f007); + else if (dev_priv->chipset == 0xa8) + gr_def(ctx, offset, 0x6cfff007); + else if (dev_priv->chipset == 0xac) + gr_def(ctx, offset, 0x0cfff007); + else + gr_def(ctx, offset, 0x0cf7f007); + if (dev_priv->chipset == 0x50) + gr_def(ctx, offset + 0x4, 0x00007fff); + else if (dev_priv->chipset < 0xa0) + gr_def(ctx, offset + 0x4, 0x003f7fff); + else + gr_def(ctx, offset + 0x4, 0x02bf7fff); + cp_ctx(ctx, offset + 0x2c, 1); + if (dev_priv->chipset == 0x50) { + cp_ctx(ctx, offset + 0x50, 9); + gr_def(ctx, offset + 0x54, 0x000003ff); + gr_def(ctx, offset + 0x58, 0x00000003); + gr_def(ctx, offset + 0x5c, 0x00000003); + gr_def(ctx, offset + 0x60, 0x000001ff); + gr_def(ctx, offset + 0x64, 0x0000001f); + gr_def(ctx, offset + 0x68, 0x0000000f); + gr_def(ctx, offset + 0x6c, 0x0000000f); + } else if(dev_priv->chipset < 0xa0) { + cp_ctx(ctx, offset + 0x50, 1); + cp_ctx(ctx, offset + 0x70, 1); + } else { + cp_ctx(ctx, offset + 0x50, 1); + cp_ctx(ctx, offset + 0x60, 5); + } + } + } +} + +static void +dd_emit(struct nouveau_grctx *ctx, int num, uint32_t val) { + int i; + if (val && ctx->mode == NOUVEAU_GRCTX_VALS) + for (i = 0; i < num; i++) + nv_wv32(ctx->data, 4 * (ctx->ctxvals_pos + i), val); + ctx->ctxvals_pos += num; +} + +static void +nv50_graph_construct_mmio_ddata(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int base, num; + base = ctx->ctxvals_pos; + + /* tesla state */ + dd_emit(ctx, 1, 0); /* 00000001 UNK0F90 */ + dd_emit(ctx, 1, 0); /* 00000001 UNK135C */ + + /* SRC_TIC state */ + dd_emit(ctx, 1, 0); /* 00000007 SRC_TILE_MODE_Z */ + dd_emit(ctx, 1, 2); /* 00000007 SRC_TILE_MODE_Y */ + dd_emit(ctx, 1, 1); /* 00000001 SRC_LINEAR #1 */ + dd_emit(ctx, 1, 0); /* 000000ff SRC_ADDRESS_HIGH */ + dd_emit(ctx, 1, 0); /* 00000001 SRC_SRGB */ + if (dev_priv->chipset >= 0x94) + dd_emit(ctx, 1, 0); /* 00000003 eng2d UNK0258 */ + dd_emit(ctx, 1, 1); /* 00000fff SRC_DEPTH */ + dd_emit(ctx, 1, 0x100); /* 0000ffff SRC_HEIGHT */ + + /* turing state */ + dd_emit(ctx, 1, 0); /* 0000000f TEXTURES_LOG2 */ + dd_emit(ctx, 1, 0); /* 0000000f SAMPLERS_LOG2 */ + dd_emit(ctx, 1, 0); /* 000000ff CB_DEF_ADDRESS_HIGH */ + dd_emit(ctx, 1, 0); /* ffffffff CB_DEF_ADDRESS_LOW */ + dd_emit(ctx, 1, 0); /* ffffffff SHARED_SIZE */ + dd_emit(ctx, 1, 2); /* ffffffff REG_MODE */ + dd_emit(ctx, 1, 1); /* 0000ffff BLOCK_ALLOC_THREADS */ + dd_emit(ctx, 1, 1); /* 00000001 LANES32 */ + dd_emit(ctx, 1, 0); /* 000000ff UNK370 */ + dd_emit(ctx, 1, 0); /* 000000ff USER_PARAM_UNK */ + dd_emit(ctx, 1, 0); /* 000000ff USER_PARAM_COUNT */ + dd_emit(ctx, 1, 1); /* 000000ff UNK384 bits 8-15 */ + dd_emit(ctx, 1, 0x3fffff); /* 003fffff TIC_LIMIT */ + dd_emit(ctx, 1, 0x1fff); /* 000fffff TSC_LIMIT */ + dd_emit(ctx, 1, 0); /* 0000ffff CB_ADDR_INDEX */ + dd_emit(ctx, 1, 1); /* 000007ff BLOCKDIM_X */ + dd_emit(ctx, 1, 1); /* 000007ff BLOCKDIM_XMY */ + dd_emit(ctx, 1, 0); /* 00000001 BLOCKDIM_XMY_OVERFLOW */ + dd_emit(ctx, 1, 1); /* 0003ffff BLOCKDIM_XMYMZ */ + dd_emit(ctx, 1, 1); /* 000007ff BLOCKDIM_Y */ + dd_emit(ctx, 1, 1); /* 0000007f BLOCKDIM_Z */ + dd_emit(ctx, 1, 4); /* 000000ff CP_REG_ALLOC_TEMP */ + dd_emit(ctx, 1, 1); /* 00000001 BLOCKDIM_DIRTY */ + if (IS_NVA3F(dev_priv->chipset)) + dd_emit(ctx, 1, 0); /* 00000003 UNK03E8 */ + dd_emit(ctx, 1, 1); /* 0000007f BLOCK_ALLOC_HALFWARPS */ + dd_emit(ctx, 1, 1); /* 00000007 LOCAL_WARPS_NO_CLAMP */ + dd_emit(ctx, 1, 7); /* 00000007 LOCAL_WARPS_LOG_ALLOC */ + dd_emit(ctx, 1, 1); /* 00000007 STACK_WARPS_NO_CLAMP */ + dd_emit(ctx, 1, 7); /* 00000007 STACK_WARPS_LOG_ALLOC */ + dd_emit(ctx, 1, 1); /* 00001fff BLOCK_ALLOC_REGSLOTS_PACKED */ + dd_emit(ctx, 1, 1); /* 00001fff BLOCK_ALLOC_REGSLOTS_STRIDED */ + dd_emit(ctx, 1, 1); /* 000007ff BLOCK_ALLOC_THREADS */ + + /* compat 2d state */ + if (dev_priv->chipset == 0x50) { + dd_emit(ctx, 4, 0); /* 0000ffff clip X, Y, W, H */ + + dd_emit(ctx, 1, 1); /* ffffffff chroma COLOR_FORMAT */ + + dd_emit(ctx, 1, 1); /* ffffffff pattern COLOR_FORMAT */ + dd_emit(ctx, 1, 0); /* ffffffff pattern SHAPE */ + dd_emit(ctx, 1, 1); /* ffffffff pattern PATTERN_SELECT */ + + dd_emit(ctx, 1, 0xa); /* ffffffff surf2d SRC_FORMAT */ + dd_emit(ctx, 1, 0); /* ffffffff surf2d DMA_SRC */ + dd_emit(ctx, 1, 0); /* 000000ff surf2d SRC_ADDRESS_HIGH */ + dd_emit(ctx, 1, 0); /* ffffffff surf2d SRC_ADDRESS_LOW */ + dd_emit(ctx, 1, 0x40); /* 0000ffff surf2d SRC_PITCH */ + dd_emit(ctx, 1, 0); /* 0000000f surf2d SRC_TILE_MODE_Z */ + dd_emit(ctx, 1, 2); /* 0000000f surf2d SRC_TILE_MODE_Y */ + dd_emit(ctx, 1, 0x100); /* ffffffff surf2d SRC_HEIGHT */ + dd_emit(ctx, 1, 1); /* 00000001 surf2d SRC_LINEAR */ + dd_emit(ctx, 1, 0x100); /* ffffffff surf2d SRC_WIDTH */ + + dd_emit(ctx, 1, 0); /* 0000ffff gdirect CLIP_B_X */ + dd_emit(ctx, 1, 0); /* 0000ffff gdirect CLIP_B_Y */ + dd_emit(ctx, 1, 0); /* 0000ffff gdirect CLIP_C_X */ + dd_emit(ctx, 1, 0); /* 0000ffff gdirect CLIP_C_Y */ + dd_emit(ctx, 1, 0); /* 0000ffff gdirect CLIP_D_X */ + dd_emit(ctx, 1, 0); /* 0000ffff gdirect CLIP_D_Y */ + dd_emit(ctx, 1, 1); /* ffffffff gdirect COLOR_FORMAT */ + dd_emit(ctx, 1, 0); /* ffffffff gdirect OPERATION */ + dd_emit(ctx, 1, 0); /* 0000ffff gdirect POINT_X */ + dd_emit(ctx, 1, 0); /* 0000ffff gdirect POINT_Y */ + + dd_emit(ctx, 1, 0); /* 0000ffff blit SRC_Y */ + dd_emit(ctx, 1, 0); /* ffffffff blit OPERATION */ + + dd_emit(ctx, 1, 0); /* ffffffff ifc OPERATION */ + + dd_emit(ctx, 1, 0); /* ffffffff iifc INDEX_FORMAT */ + dd_emit(ctx, 1, 0); /* ffffffff iifc LUT_OFFSET */ + dd_emit(ctx, 1, 4); /* ffffffff iifc COLOR_FORMAT */ + dd_emit(ctx, 1, 0); /* ffffffff iifc OPERATION */ + } + + /* m2mf state */ + dd_emit(ctx, 1, 0); /* ffffffff m2mf LINE_COUNT */ + dd_emit(ctx, 1, 0); /* ffffffff m2mf LINE_LENGTH_IN */ + dd_emit(ctx, 2, 0); /* ffffffff m2mf OFFSET_IN, OFFSET_OUT */ + dd_emit(ctx, 1, 1); /* ffffffff m2mf TILING_DEPTH_OUT */ + dd_emit(ctx, 1, 0x100); /* ffffffff m2mf TILING_HEIGHT_OUT */ + dd_emit(ctx, 1, 0); /* ffffffff m2mf TILING_POSITION_OUT_Z */ + dd_emit(ctx, 1, 1); /* 00000001 m2mf LINEAR_OUT */ + dd_emit(ctx, 2, 0); /* 0000ffff m2mf TILING_POSITION_OUT_X, Y */ + dd_emit(ctx, 1, 0x100); /* ffffffff m2mf TILING_PITCH_OUT */ + dd_emit(ctx, 1, 1); /* ffffffff m2mf TILING_DEPTH_IN */ + dd_emit(ctx, 1, 0x100); /* ffffffff m2mf TILING_HEIGHT_IN */ + dd_emit(ctx, 1, 0); /* ffffffff m2mf TILING_POSITION_IN_Z */ + dd_emit(ctx, 1, 1); /* 00000001 m2mf LINEAR_IN */ + dd_emit(ctx, 2, 0); /* 0000ffff m2mf TILING_POSITION_IN_X, Y */ + dd_emit(ctx, 1, 0x100); /* ffffffff m2mf TILING_PITCH_IN */ + + /* more compat 2d state */ + if (dev_priv->chipset == 0x50) { + dd_emit(ctx, 1, 1); /* ffffffff line COLOR_FORMAT */ + dd_emit(ctx, 1, 0); /* ffffffff line OPERATION */ + + dd_emit(ctx, 1, 1); /* ffffffff triangle COLOR_FORMAT */ + dd_emit(ctx, 1, 0); /* ffffffff triangle OPERATION */ + + dd_emit(ctx, 1, 0); /* 0000000f sifm TILE_MODE_Z */ + dd_emit(ctx, 1, 2); /* 0000000f sifm TILE_MODE_Y */ + dd_emit(ctx, 1, 0); /* 000000ff sifm FORMAT_FILTER */ + dd_emit(ctx, 1, 1); /* 000000ff sifm FORMAT_ORIGIN */ + dd_emit(ctx, 1, 0); /* 0000ffff sifm SRC_PITCH */ + dd_emit(ctx, 1, 1); /* 00000001 sifm SRC_LINEAR */ + dd_emit(ctx, 1, 0); /* 000000ff sifm SRC_OFFSET_HIGH */ + dd_emit(ctx, 1, 0); /* ffffffff sifm SRC_OFFSET */ + dd_emit(ctx, 1, 0); /* 0000ffff sifm SRC_HEIGHT */ + dd_emit(ctx, 1, 0); /* 0000ffff sifm SRC_WIDTH */ + dd_emit(ctx, 1, 3); /* ffffffff sifm COLOR_FORMAT */ + dd_emit(ctx, 1, 0); /* ffffffff sifm OPERATION */ + + dd_emit(ctx, 1, 0); /* ffffffff sifc OPERATION */ + } + + /* tesla state */ + dd_emit(ctx, 1, 0); /* 0000000f GP_TEXTURES_LOG2 */ + dd_emit(ctx, 1, 0); /* 0000000f GP_SAMPLERS_LOG2 */ + dd_emit(ctx, 1, 0); /* 000000ff */ + dd_emit(ctx, 1, 0); /* ffffffff */ + dd_emit(ctx, 1, 4); /* 000000ff UNK12B0_0 */ + dd_emit(ctx, 1, 0x70); /* 000000ff UNK12B0_1 */ + dd_emit(ctx, 1, 0x80); /* 000000ff UNK12B0_3 */ + dd_emit(ctx, 1, 0); /* 000000ff UNK12B0_2 */ + dd_emit(ctx, 1, 0); /* 0000000f FP_TEXTURES_LOG2 */ + dd_emit(ctx, 1, 0); /* 0000000f FP_SAMPLERS_LOG2 */ + if (IS_NVA3F(dev_priv->chipset)) { + dd_emit(ctx, 1, 0); /* ffffffff */ + dd_emit(ctx, 1, 0); /* 0000007f MULTISAMPLE_SAMPLES_LOG2 */ + } else { + dd_emit(ctx, 1, 0); /* 0000000f MULTISAMPLE_SAMPLES_LOG2 */ + } + dd_emit(ctx, 1, 0xc); /* 000000ff SEMANTIC_COLOR.BFC0_ID */ + if (dev_priv->chipset != 0x50) + dd_emit(ctx, 1, 0); /* 00000001 SEMANTIC_COLOR.CLMP_EN */ + dd_emit(ctx, 1, 8); /* 000000ff SEMANTIC_COLOR.COLR_NR */ + dd_emit(ctx, 1, 0x14); /* 000000ff SEMANTIC_COLOR.FFC0_ID */ + if (dev_priv->chipset == 0x50) { + dd_emit(ctx, 1, 0); /* 000000ff SEMANTIC_LAYER */ + dd_emit(ctx, 1, 0); /* 00000001 */ + } else { + dd_emit(ctx, 1, 0); /* 00000001 SEMANTIC_PTSZ.ENABLE */ + dd_emit(ctx, 1, 0x29); /* 000000ff SEMANTIC_PTSZ.PTSZ_ID */ + dd_emit(ctx, 1, 0x27); /* 000000ff SEMANTIC_PRIM */ + dd_emit(ctx, 1, 0x26); /* 000000ff SEMANTIC_LAYER */ + dd_emit(ctx, 1, 8); /* 0000000f SMENATIC_CLIP.CLIP_HIGH */ + dd_emit(ctx, 1, 4); /* 000000ff SEMANTIC_CLIP.CLIP_LO */ + dd_emit(ctx, 1, 0x27); /* 000000ff UNK0FD4 */ + dd_emit(ctx, 1, 0); /* 00000001 UNK1900 */ + } + dd_emit(ctx, 1, 0); /* 00000007 RT_CONTROL_MAP0 */ + dd_emit(ctx, 1, 1); /* 00000007 RT_CONTROL_MAP1 */ + dd_emit(ctx, 1, 2); /* 00000007 RT_CONTROL_MAP2 */ + dd_emit(ctx, 1, 3); /* 00000007 RT_CONTROL_MAP3 */ + dd_emit(ctx, 1, 4); /* 00000007 RT_CONTROL_MAP4 */ + dd_emit(ctx, 1, 5); /* 00000007 RT_CONTROL_MAP5 */ + dd_emit(ctx, 1, 6); /* 00000007 RT_CONTROL_MAP6 */ + dd_emit(ctx, 1, 7); /* 00000007 RT_CONTROL_MAP7 */ + dd_emit(ctx, 1, 1); /* 0000000f RT_CONTROL_COUNT */ + dd_emit(ctx, 8, 0); /* 00000001 RT_HORIZ_UNK */ + dd_emit(ctx, 8, 0); /* ffffffff RT_ADDRESS_LOW */ + dd_emit(ctx, 1, 0xcf); /* 000000ff RT_FORMAT */ + dd_emit(ctx, 7, 0); /* 000000ff RT_FORMAT */ + if (dev_priv->chipset != 0x50) + dd_emit(ctx, 3, 0); /* 1, 1, 1 */ + else + dd_emit(ctx, 2, 0); /* 1, 1 */ + dd_emit(ctx, 1, 0); /* ffffffff GP_ENABLE */ + dd_emit(ctx, 1, 0x80); /* 0000ffff GP_VERTEX_OUTPUT_COUNT*/ + dd_emit(ctx, 1, 4); /* 000000ff GP_REG_ALLOC_RESULT */ + dd_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + if (IS_NVA3F(dev_priv->chipset)) { + dd_emit(ctx, 1, 3); /* 00000003 */ + dd_emit(ctx, 1, 0); /* 00000001 UNK1418. Alone. */ + } + if (dev_priv->chipset != 0x50) + dd_emit(ctx, 1, 3); /* 00000003 UNK15AC */ + dd_emit(ctx, 1, 1); /* ffffffff RASTERIZE_ENABLE */ + dd_emit(ctx, 1, 0); /* 00000001 FP_CONTROL.EXPORTS_Z */ + if (dev_priv->chipset != 0x50) + dd_emit(ctx, 1, 0); /* 00000001 FP_CONTROL.MULTIPLE_RESULTS */ + dd_emit(ctx, 1, 0x12); /* 000000ff FP_INTERPOLANT_CTRL.COUNT */ + dd_emit(ctx, 1, 0x10); /* 000000ff FP_INTERPOLANT_CTRL.COUNT_NONFLAT */ + dd_emit(ctx, 1, 0xc); /* 000000ff FP_INTERPOLANT_CTRL.OFFSET */ + dd_emit(ctx, 1, 1); /* 00000001 FP_INTERPOLANT_CTRL.UMASK.W */ + dd_emit(ctx, 1, 0); /* 00000001 FP_INTERPOLANT_CTRL.UMASK.X */ + dd_emit(ctx, 1, 0); /* 00000001 FP_INTERPOLANT_CTRL.UMASK.Y */ + dd_emit(ctx, 1, 0); /* 00000001 FP_INTERPOLANT_CTRL.UMASK.Z */ + dd_emit(ctx, 1, 4); /* 000000ff FP_RESULT_COUNT */ + dd_emit(ctx, 1, 2); /* ffffffff REG_MODE */ + dd_emit(ctx, 1, 4); /* 000000ff FP_REG_ALLOC_TEMP */ + if (dev_priv->chipset >= 0xa0) + dd_emit(ctx, 1, 0); /* ffffffff */ + dd_emit(ctx, 1, 0); /* 00000001 GP_BUILTIN_RESULT_EN.LAYER_IDX */ + dd_emit(ctx, 1, 0); /* ffffffff STRMOUT_ENABLE */ + dd_emit(ctx, 1, 0x3fffff); /* 003fffff TIC_LIMIT */ + dd_emit(ctx, 1, 0x1fff); /* 000fffff TSC_LIMIT */ + dd_emit(ctx, 1, 0); /* 00000001 VERTEX_TWO_SIDE_ENABLE*/ + if (dev_priv->chipset != 0x50) + dd_emit(ctx, 8, 0); /* 00000001 */ + if (dev_priv->chipset >= 0xa0) { + dd_emit(ctx, 1, 1); /* 00000007 VTX_ATTR_DEFINE.COMP */ + dd_emit(ctx, 1, 1); /* 00000007 VTX_ATTR_DEFINE.SIZE */ + dd_emit(ctx, 1, 2); /* 00000007 VTX_ATTR_DEFINE.TYPE */ + dd_emit(ctx, 1, 0); /* 000000ff VTX_ATTR_DEFINE.ATTR */ + } + dd_emit(ctx, 1, 4); /* 0000007f VP_RESULT_MAP_SIZE */ + dd_emit(ctx, 1, 0x14); /* 0000001f ZETA_FORMAT */ + dd_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + dd_emit(ctx, 1, 0); /* 0000000f VP_TEXTURES_LOG2 */ + dd_emit(ctx, 1, 0); /* 0000000f VP_SAMPLERS_LOG2 */ + if (IS_NVA3F(dev_priv->chipset)) + dd_emit(ctx, 1, 0); /* 00000001 */ + dd_emit(ctx, 1, 2); /* 00000003 POLYGON_MODE_BACK */ + if (dev_priv->chipset >= 0xa0) + dd_emit(ctx, 1, 0); /* 00000003 VTX_ATTR_DEFINE.SIZE - 1 */ + dd_emit(ctx, 1, 0); /* 0000ffff CB_ADDR_INDEX */ + if (dev_priv->chipset >= 0xa0) + dd_emit(ctx, 1, 0); /* 00000003 */ + dd_emit(ctx, 1, 0); /* 00000001 CULL_FACE_ENABLE */ + dd_emit(ctx, 1, 1); /* 00000003 CULL_FACE */ + dd_emit(ctx, 1, 0); /* 00000001 FRONT_FACE */ + dd_emit(ctx, 1, 2); /* 00000003 POLYGON_MODE_FRONT */ + dd_emit(ctx, 1, 0x1000); /* 00007fff UNK141C */ + if (dev_priv->chipset != 0x50) { + dd_emit(ctx, 1, 0xe00); /* 7fff */ + dd_emit(ctx, 1, 0x1000); /* 7fff */ + dd_emit(ctx, 1, 0x1e00); /* 7fff */ + } + dd_emit(ctx, 1, 0); /* 00000001 BEGIN_END_ACTIVE */ + dd_emit(ctx, 1, 1); /* 00000001 POLYGON_MODE_??? */ + dd_emit(ctx, 1, 1); /* 000000ff GP_REG_ALLOC_TEMP / 4 rounded up */ + dd_emit(ctx, 1, 1); /* 000000ff FP_REG_ALLOC_TEMP... without /4? */ + dd_emit(ctx, 1, 1); /* 000000ff VP_REG_ALLOC_TEMP / 4 rounded up */ + dd_emit(ctx, 1, 1); /* 00000001 */ + dd_emit(ctx, 1, 0); /* 00000001 */ + dd_emit(ctx, 1, 0); /* 00000001 VTX_ATTR_MASK_UNK0 nonempty */ + dd_emit(ctx, 1, 0); /* 00000001 VTX_ATTR_MASK_UNK1 nonempty */ + dd_emit(ctx, 1, 0x200); /* 0003ffff GP_VERTEX_OUTPUT_COUNT*GP_REG_ALLOC_RESULT */ + if (IS_NVA3F(dev_priv->chipset)) + dd_emit(ctx, 1, 0x200); + dd_emit(ctx, 1, 0); /* 00000001 */ + if (dev_priv->chipset < 0xa0) { + dd_emit(ctx, 1, 1); /* 00000001 */ + dd_emit(ctx, 1, 0x70); /* 000000ff */ + dd_emit(ctx, 1, 0x80); /* 000000ff */ + dd_emit(ctx, 1, 0); /* 000000ff */ + dd_emit(ctx, 1, 0); /* 00000001 */ + dd_emit(ctx, 1, 1); /* 00000001 */ + dd_emit(ctx, 1, 0x70); /* 000000ff */ + dd_emit(ctx, 1, 0x80); /* 000000ff */ + dd_emit(ctx, 1, 0); /* 000000ff */ + } else { + dd_emit(ctx, 1, 1); /* 00000001 */ + dd_emit(ctx, 1, 0xf0); /* 000000ff */ + dd_emit(ctx, 1, 0xff); /* 000000ff */ + dd_emit(ctx, 1, 0); /* 000000ff */ + dd_emit(ctx, 1, 0); /* 00000001 */ + dd_emit(ctx, 1, 1); /* 00000001 */ + dd_emit(ctx, 1, 0xf0); /* 000000ff */ + dd_emit(ctx, 1, 0xff); /* 000000ff */ + dd_emit(ctx, 1, 0); /* 000000ff */ + dd_emit(ctx, 1, 9); /* 0000003f UNK114C.COMP,SIZE */ + } + + /* eng2d state */ + dd_emit(ctx, 1, 0); /* 00000001 eng2d COLOR_KEY_ENABLE */ + dd_emit(ctx, 1, 0); /* 00000007 eng2d COLOR_KEY_FORMAT */ + dd_emit(ctx, 1, 1); /* ffffffff eng2d DST_DEPTH */ + dd_emit(ctx, 1, 0xcf); /* 000000ff eng2d DST_FORMAT */ + dd_emit(ctx, 1, 0); /* ffffffff eng2d DST_LAYER */ + dd_emit(ctx, 1, 1); /* 00000001 eng2d DST_LINEAR */ + dd_emit(ctx, 1, 0); /* 00000007 eng2d PATTERN_COLOR_FORMAT */ + dd_emit(ctx, 1, 0); /* 00000007 eng2d OPERATION */ + dd_emit(ctx, 1, 0); /* 00000003 eng2d PATTERN_SELECT */ + dd_emit(ctx, 1, 0xcf); /* 000000ff eng2d SIFC_FORMAT */ + dd_emit(ctx, 1, 0); /* 00000001 eng2d SIFC_BITMAP_ENABLE */ + dd_emit(ctx, 1, 2); /* 00000003 eng2d SIFC_BITMAP_UNK808 */ + dd_emit(ctx, 1, 0); /* ffffffff eng2d BLIT_DU_DX_FRACT */ + dd_emit(ctx, 1, 1); /* ffffffff eng2d BLIT_DU_DX_INT */ + dd_emit(ctx, 1, 0); /* ffffffff eng2d BLIT_DV_DY_FRACT */ + dd_emit(ctx, 1, 1); /* ffffffff eng2d BLIT_DV_DY_INT */ + dd_emit(ctx, 1, 0); /* 00000001 eng2d BLIT_CONTROL_FILTER */ + dd_emit(ctx, 1, 0xcf); /* 000000ff eng2d DRAW_COLOR_FORMAT */ + dd_emit(ctx, 1, 0xcf); /* 000000ff eng2d SRC_FORMAT */ + dd_emit(ctx, 1, 1); /* 00000001 eng2d SRC_LINEAR #2 */ + + num = ctx->ctxvals_pos - base; + ctx->ctxvals_pos = base; + if (IS_NVA3F(dev_priv->chipset)) + cp_ctx(ctx, 0x404800, num); + else + cp_ctx(ctx, 0x405400, num); +} + +/* + * xfer areas. These are a pain. + * + * There are 2 xfer areas: the first one is big and contains all sorts of + * stuff, the second is small and contains some per-TP context. + * + * Each area is split into 8 "strands". The areas, when saved to grctx, + * are made of 8-word blocks. Each block contains a single word from + * each strand. The strands are independent of each other, their + * addresses are unrelated to each other, and data in them is closely + * packed together. The strand layout varies a bit between cards: here + * and there, a single word is thrown out in the middle and the whole + * strand is offset by a bit from corresponding one on another chipset. + * For this reason, addresses of stuff in strands are almost useless. + * Knowing sequence of stuff and size of gaps between them is much more + * useful, and that's how we build the strands in our generator. + * + * NVA0 takes this mess to a whole new level by cutting the old strands + * into a few dozen pieces [known as genes], rearranging them randomly, + * and putting them back together to make new strands. Hopefully these + * genes correspond more or less directly to the same PGRAPH subunits + * as in 400040 register. + * + * The most common value in default context is 0, and when the genes + * are separated by 0's, gene bounduaries are quite speculative... + * some of them can be clearly deduced, others can be guessed, and yet + * others won't be resolved without figuring out the real meaning of + * given ctxval. For the same reason, ending point of each strand + * is unknown. Except for strand 0, which is the longest strand and + * its end corresponds to end of the whole xfer. + * + * An unsolved mystery is the seek instruction: it takes an argument + * in bits 8-18, and that argument is clearly the place in strands to + * seek to... but the offsets don't seem to correspond to offsets as + * seen in grctx. Perhaps there's another, real, not randomly-changing + * addressing in strands, and the xfer insn just happens to skip over + * the unused bits? NV10-NV30 PIPE comes to mind... + * + * As far as I know, there's no way to access the xfer areas directly + * without the help of ctxprog. + */ + +static void +xf_emit(struct nouveau_grctx *ctx, int num, uint32_t val) { + int i; + if (val && ctx->mode == NOUVEAU_GRCTX_VALS) + for (i = 0; i < num; i++) + nv_wv32(ctx->data, 4 * (ctx->ctxvals_pos + (i << 3)), val); + ctx->ctxvals_pos += num << 3; +} + +/* Gene declarations... */ + +static void nv50_graph_construct_gene_dispatch(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_m2mf(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_ccache(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_unk10xx(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_unk14xx(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_zcull(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_clipid(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_unk24xx(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_vfetch(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_eng2d(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_csched(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_unk1cxx(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_strmout(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_unk34xx(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_ropm1(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_ropm2(struct nouveau_grctx *ctx); +static void nv50_graph_construct_gene_ropc(struct nouveau_grctx *ctx); +static void nv50_graph_construct_xfer_tp(struct nouveau_grctx *ctx); + +static void +nv50_graph_construct_xfer1(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int i; + int offset; + int size = 0; + uint32_t units = nv_rd32 (ctx->dev, 0x1540); + + offset = (ctx->ctxvals_pos+0x3f)&~0x3f; + ctx->ctxvals_base = offset; + + if (dev_priv->chipset < 0xa0) { + /* Strand 0 */ + ctx->ctxvals_pos = offset; + nv50_graph_construct_gene_dispatch(ctx); + nv50_graph_construct_gene_m2mf(ctx); + nv50_graph_construct_gene_unk24xx(ctx); + nv50_graph_construct_gene_clipid(ctx); + nv50_graph_construct_gene_zcull(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 1 */ + ctx->ctxvals_pos = offset + 0x1; + nv50_graph_construct_gene_vfetch(ctx); + nv50_graph_construct_gene_eng2d(ctx); + nv50_graph_construct_gene_csched(ctx); + nv50_graph_construct_gene_ropm1(ctx); + nv50_graph_construct_gene_ropm2(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 2 */ + ctx->ctxvals_pos = offset + 0x2; + nv50_graph_construct_gene_ccache(ctx); + nv50_graph_construct_gene_unk1cxx(ctx); + nv50_graph_construct_gene_strmout(ctx); + nv50_graph_construct_gene_unk14xx(ctx); + nv50_graph_construct_gene_unk10xx(ctx); + nv50_graph_construct_gene_unk34xx(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 3: per-ROP group state */ + ctx->ctxvals_pos = offset + 3; + for (i = 0; i < 6; i++) + if (units & (1 << (i + 16))) + nv50_graph_construct_gene_ropc(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strands 4-7: per-TP state */ + for (i = 0; i < 4; i++) { + ctx->ctxvals_pos = offset + 4 + i; + if (units & (1 << (2 * i))) + nv50_graph_construct_xfer_tp(ctx); + if (units & (1 << (2 * i + 1))) + nv50_graph_construct_xfer_tp(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + } + } else { + /* Strand 0 */ + ctx->ctxvals_pos = offset; + nv50_graph_construct_gene_dispatch(ctx); + nv50_graph_construct_gene_m2mf(ctx); + nv50_graph_construct_gene_unk34xx(ctx); + nv50_graph_construct_gene_csched(ctx); + nv50_graph_construct_gene_unk1cxx(ctx); + nv50_graph_construct_gene_strmout(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 1 */ + ctx->ctxvals_pos = offset + 1; + nv50_graph_construct_gene_unk10xx(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 2 */ + ctx->ctxvals_pos = offset + 2; + if (dev_priv->chipset == 0xa0) + nv50_graph_construct_gene_unk14xx(ctx); + nv50_graph_construct_gene_unk24xx(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 3 */ + ctx->ctxvals_pos = offset + 3; + nv50_graph_construct_gene_vfetch(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 4 */ + ctx->ctxvals_pos = offset + 4; + nv50_graph_construct_gene_ccache(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 5 */ + ctx->ctxvals_pos = offset + 5; + nv50_graph_construct_gene_ropm2(ctx); + nv50_graph_construct_gene_ropm1(ctx); + /* per-ROP context */ + for (i = 0; i < 8; i++) + if (units & (1<<(i+16))) + nv50_graph_construct_gene_ropc(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 6 */ + ctx->ctxvals_pos = offset + 6; + nv50_graph_construct_gene_zcull(ctx); + nv50_graph_construct_gene_clipid(ctx); + nv50_graph_construct_gene_eng2d(ctx); + if (units & (1 << 0)) + nv50_graph_construct_xfer_tp(ctx); + if (units & (1 << 1)) + nv50_graph_construct_xfer_tp(ctx); + if (units & (1 << 2)) + nv50_graph_construct_xfer_tp(ctx); + if (units & (1 << 3)) + nv50_graph_construct_xfer_tp(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 7 */ + ctx->ctxvals_pos = offset + 7; + if (dev_priv->chipset == 0xa0) { + if (units & (1 << 4)) + nv50_graph_construct_xfer_tp(ctx); + if (units & (1 << 5)) + nv50_graph_construct_xfer_tp(ctx); + if (units & (1 << 6)) + nv50_graph_construct_xfer_tp(ctx); + if (units & (1 << 7)) + nv50_graph_construct_xfer_tp(ctx); + if (units & (1 << 8)) + nv50_graph_construct_xfer_tp(ctx); + if (units & (1 << 9)) + nv50_graph_construct_xfer_tp(ctx); + } else { + nv50_graph_construct_gene_unk14xx(ctx); + } + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + } + + ctx->ctxvals_pos = offset + size * 8; + ctx->ctxvals_pos = (ctx->ctxvals_pos+0x3f)&~0x3f; + cp_lsr (ctx, offset); + cp_out (ctx, CP_SET_XFER_POINTER); + cp_lsr (ctx, size); + cp_out (ctx, CP_SEEK_1); + cp_out (ctx, CP_XFER_1); + cp_wait(ctx, XFER, BUSY); +} + +/* + * non-trivial demagiced parts of ctx init go here + */ + +static void +nv50_graph_construct_gene_dispatch(struct nouveau_grctx *ctx) +{ + /* start of strand 0 */ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + /* SEEK */ + if (dev_priv->chipset == 0x50) + xf_emit(ctx, 5, 0); + else if (!IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 6, 0); + else + xf_emit(ctx, 4, 0); + /* SEEK */ + /* the PGRAPH's internal FIFO */ + if (dev_priv->chipset == 0x50) + xf_emit(ctx, 8*3, 0); + else + xf_emit(ctx, 0x100*3, 0); + /* and another bonus slot?!? */ + xf_emit(ctx, 3, 0); + /* and YET ANOTHER bonus slot? */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 3, 0); + /* SEEK */ + /* CTX_SWITCH: caches of gr objects bound to subchannels. 8 values, last used index */ + xf_emit(ctx, 9, 0); + /* SEEK */ + xf_emit(ctx, 9, 0); + /* SEEK */ + xf_emit(ctx, 9, 0); + /* SEEK */ + xf_emit(ctx, 9, 0); + /* SEEK */ + if (dev_priv->chipset < 0x90) + xf_emit(ctx, 4, 0); + /* SEEK */ + xf_emit(ctx, 2, 0); + /* SEEK */ + xf_emit(ctx, 6*2, 0); + xf_emit(ctx, 2, 0); + /* SEEK */ + xf_emit(ctx, 2, 0); + /* SEEK */ + xf_emit(ctx, 6*2, 0); + xf_emit(ctx, 2, 0); + /* SEEK */ + if (dev_priv->chipset == 0x50) + xf_emit(ctx, 0x1c, 0); + else if (dev_priv->chipset < 0xa0) + xf_emit(ctx, 0x1e, 0); + else + xf_emit(ctx, 0x22, 0); + /* SEEK */ + xf_emit(ctx, 0x15, 0); +} + +static void +nv50_graph_construct_gene_m2mf(struct nouveau_grctx *ctx) +{ + /* Strand 0, right after dispatch */ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int smallm2mf = 0; + if (dev_priv->chipset < 0x92 || dev_priv->chipset == 0x98) + smallm2mf = 1; + /* SEEK */ + xf_emit (ctx, 1, 0); /* DMA_NOTIFY instance >> 4 */ + xf_emit (ctx, 1, 0); /* DMA_BUFFER_IN instance >> 4 */ + xf_emit (ctx, 1, 0); /* DMA_BUFFER_OUT instance >> 4 */ + xf_emit (ctx, 1, 0); /* OFFSET_IN */ + xf_emit (ctx, 1, 0); /* OFFSET_OUT */ + xf_emit (ctx, 1, 0); /* PITCH_IN */ + xf_emit (ctx, 1, 0); /* PITCH_OUT */ + xf_emit (ctx, 1, 0); /* LINE_LENGTH */ + xf_emit (ctx, 1, 0); /* LINE_COUNT */ + xf_emit (ctx, 1, 0x21); /* FORMAT: bits 0-4 INPUT_INC, bits 5-9 OUTPUT_INC */ + xf_emit (ctx, 1, 1); /* LINEAR_IN */ + xf_emit (ctx, 1, 0x2); /* TILING_MODE_IN: bits 0-2 y tiling, bits 3-5 z tiling */ + xf_emit (ctx, 1, 0x100); /* TILING_PITCH_IN */ + xf_emit (ctx, 1, 0x100); /* TILING_HEIGHT_IN */ + xf_emit (ctx, 1, 1); /* TILING_DEPTH_IN */ + xf_emit (ctx, 1, 0); /* TILING_POSITION_IN_Z */ + xf_emit (ctx, 1, 0); /* TILING_POSITION_IN */ + xf_emit (ctx, 1, 1); /* LINEAR_OUT */ + xf_emit (ctx, 1, 0x2); /* TILING_MODE_OUT: bits 0-2 y tiling, bits 3-5 z tiling */ + xf_emit (ctx, 1, 0x100); /* TILING_PITCH_OUT */ + xf_emit (ctx, 1, 0x100); /* TILING_HEIGHT_OUT */ + xf_emit (ctx, 1, 1); /* TILING_DEPTH_OUT */ + xf_emit (ctx, 1, 0); /* TILING_POSITION_OUT_Z */ + xf_emit (ctx, 1, 0); /* TILING_POSITION_OUT */ + xf_emit (ctx, 1, 0); /* OFFSET_IN_HIGH */ + xf_emit (ctx, 1, 0); /* OFFSET_OUT_HIGH */ + /* SEEK */ + if (smallm2mf) + xf_emit(ctx, 0x40, 0); /* 20 * ffffffff, 3ffff */ + else + xf_emit(ctx, 0x100, 0); /* 80 * ffffffff, 3ffff */ + xf_emit(ctx, 4, 0); /* 1f/7f, 0, 1f/7f, 0 [1f for smallm2mf, 7f otherwise] */ + /* SEEK */ + if (smallm2mf) + xf_emit(ctx, 0x400, 0); /* ffffffff */ + else + xf_emit(ctx, 0x800, 0); /* ffffffff */ + xf_emit(ctx, 4, 0); /* ff/1ff, 0, 0, 0 [ff for smallm2mf, 1ff otherwise] */ + /* SEEK */ + xf_emit(ctx, 0x40, 0); /* 20 * bits ffffffff, 3ffff */ + xf_emit(ctx, 0x6, 0); /* 1f, 0, 1f, 0, 1f, 0 */ +} + +static void +nv50_graph_construct_gene_ccache(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + xf_emit(ctx, 2, 0); /* RO */ + xf_emit(ctx, 0x800, 0); /* ffffffff */ + switch (dev_priv->chipset) { + case 0x50: + case 0x92: + case 0xa0: + xf_emit(ctx, 0x2b, 0); + break; + case 0x84: + xf_emit(ctx, 0x29, 0); + break; + case 0x94: + case 0x96: + case 0xa3: + xf_emit(ctx, 0x27, 0); + break; + case 0x86: + case 0x98: + case 0xa5: + case 0xa8: + case 0xaa: + case 0xac: + case 0xaf: + xf_emit(ctx, 0x25, 0); + break; + } + /* CB bindings, 0x80 of them. first word is address >> 8, second is + * size >> 4 | valid << 24 */ + xf_emit(ctx, 0x100, 0); /* ffffffff CB_DEF */ + xf_emit(ctx, 1, 0); /* 0000007f CB_ADDR_BUFFER */ + xf_emit(ctx, 1, 0); /* 0 */ + xf_emit(ctx, 0x30, 0); /* ff SET_PROGRAM_CB */ + xf_emit(ctx, 1, 0); /* 3f last SET_PROGRAM_CB */ + xf_emit(ctx, 4, 0); /* RO */ + xf_emit(ctx, 0x100, 0); /* ffffffff */ + xf_emit(ctx, 8, 0); /* 1f, 0, 0, ... */ + xf_emit(ctx, 8, 0); /* ffffffff */ + xf_emit(ctx, 4, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 3 */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_CODE_CB */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_TIC */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_TSC */ + xf_emit(ctx, 1, 0); /* 00000001 LINKED_TSC */ + xf_emit(ctx, 1, 0); /* 000000ff TIC_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff TIC_ADDRESS_LOW */ + xf_emit(ctx, 1, 0x3fffff); /* 003fffff TIC_LIMIT */ + xf_emit(ctx, 1, 0); /* 000000ff TSC_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff TSC_ADDRESS_LOW */ + xf_emit(ctx, 1, 0x1fff); /* 000fffff TSC_LIMIT */ + xf_emit(ctx, 1, 0); /* 000000ff VP_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff VP_ADDRESS_LOW */ + xf_emit(ctx, 1, 0); /* 00ffffff VP_START_ID */ + xf_emit(ctx, 1, 0); /* 000000ff CB_DEF_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff CB_DEF_ADDRESS_LOW */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0); /* 000000ff GP_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff GP_ADDRESS_LOW */ + xf_emit(ctx, 1, 0); /* 00ffffff GP_START_ID */ + xf_emit(ctx, 1, 0); /* 000000ff FP_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff FP_ADDRESS_LOW */ + xf_emit(ctx, 1, 0); /* 00ffffff FP_START_ID */ +} + +static void +nv50_graph_construct_gene_unk10xx(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int i; + /* end of area 2 on pre-NVA0, area 1 on NVAx */ + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 4); /* 0000007f VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0x80); /* 0000ffff GP_VERTEX_OUTPUT_COUNT */ + xf_emit(ctx, 1, 4); /* 000000ff GP_REG_ALLOC_RESULT */ + xf_emit(ctx, 1, 0x80c14); /* 01ffffff SEMANTIC_COLOR */ + xf_emit(ctx, 1, 0); /* 00000001 VERTEX_TWO_SIDE_ENABLE */ + if (dev_priv->chipset == 0x50) + xf_emit(ctx, 1, 0x3ff); + else + xf_emit(ctx, 1, 0x7ff); /* 000007ff */ + xf_emit(ctx, 1, 0); /* 111/113 */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + for (i = 0; i < 8; i++) { + switch (dev_priv->chipset) { + case 0x50: + case 0x86: + case 0x98: + case 0xaa: + case 0xac: + xf_emit(ctx, 0xa0, 0); /* ffffffff */ + break; + case 0x84: + case 0x92: + case 0x94: + case 0x96: + xf_emit(ctx, 0x120, 0); + break; + case 0xa5: + case 0xa8: + xf_emit(ctx, 0x100, 0); /* ffffffff */ + break; + case 0xa0: + case 0xa3: + case 0xaf: + xf_emit(ctx, 0x400, 0); /* ffffffff */ + break; + } + xf_emit(ctx, 4, 0); /* 3f, 0, 0, 0 */ + xf_emit(ctx, 4, 0); /* ffffffff */ + } + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 4); /* 0000007f VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0x80); /* 0000ffff GP_VERTEX_OUTPUT_COUNT */ + xf_emit(ctx, 1, 4); /* 000000ff GP_REG_ALLOC_TEMP */ + xf_emit(ctx, 1, 1); /* 00000001 RASTERIZE_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1900 */ + xf_emit(ctx, 1, 0x27); /* 000000ff UNK0FD4 */ + xf_emit(ctx, 1, 0); /* 0001ffff GP_BUILTIN_RESULT_EN */ + xf_emit(ctx, 1, 0x26); /* 000000ff SEMANTIC_LAYER */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ +} + +static void +nv50_graph_construct_gene_unk34xx(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + /* end of area 2 on pre-NVA0, area 1 on NVAx */ + xf_emit(ctx, 1, 0); /* 00000001 VIEWPORT_CLIP_RECTS_EN */ + xf_emit(ctx, 1, 0); /* 00000003 VIEWPORT_CLIP_MODE */ + xf_emit(ctx, 0x10, 0x04000000); /* 07ffffff VIEWPORT_CLIP_HORIZ*8, VIEWPORT_CLIP_VERT*8 */ + xf_emit(ctx, 1, 0); /* 00000001 POLYGON_STIPPLE_ENABLE */ + xf_emit(ctx, 0x20, 0); /* ffffffff POLYGON_STIPPLE */ + xf_emit(ctx, 2, 0); /* 00007fff WINDOW_OFFSET_XY */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 1, 0x04e3bfdf); /* ffffffff UNK0D64 */ + xf_emit(ctx, 1, 0x04e3bfdf); /* ffffffff UNK0DF4 */ + xf_emit(ctx, 1, 0); /* 00000003 WINDOW_ORIGIN */ + xf_emit(ctx, 1, 0); /* 00000007 */ + xf_emit(ctx, 1, 0x1fe21); /* 0001ffff tesla UNK0FAC */ + if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 1, 0x0fac6881); + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 1, 1); + xf_emit(ctx, 3, 0); + } +} + +static void +nv50_graph_construct_gene_unk14xx(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + /* middle of area 2 on pre-NVA0, beginning of area 2 on NVA0, area 7 on >NVA0 */ + if (dev_priv->chipset != 0x50) { + xf_emit(ctx, 5, 0); /* ffffffff */ + xf_emit(ctx, 1, 0x80c14); /* 01ffffff SEMANTIC_COLOR */ + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 1, 0); /* 000003ff */ + xf_emit(ctx, 1, 0x804); /* 00000fff SEMANTIC_CLIP */ + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 2, 4); /* 7f, ff */ + xf_emit(ctx, 1, 0x8100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + } + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 4); /* 0000007f VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0x10); /* 7f/ff VIEW_VOLUME_CLIP_CTRL */ + xf_emit(ctx, 1, 0); /* 000000ff VP_CLIP_DISTANCE_ENABLE */ + if (dev_priv->chipset != 0x50) + xf_emit(ctx, 1, 0); /* 3ff */ + xf_emit(ctx, 1, 0); /* 000000ff tesla UNK1940 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK0D7C */ + xf_emit(ctx, 1, 0x804); /* 00000fff SEMANTIC_CLIP */ + xf_emit(ctx, 1, 1); /* 00000001 VIEWPORT_TRANSFORM_EN */ + xf_emit(ctx, 1, 0x1a); /* 0000001f POLYGON_MODE */ + if (dev_priv->chipset != 0x50) + xf_emit(ctx, 1, 0x7f); /* 000000ff tesla UNK0FFC */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 1); /* 00000001 SHADE_MODEL */ + xf_emit(ctx, 1, 0x80c14); /* 01ffffff SEMANTIC_COLOR */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1900 */ + xf_emit(ctx, 1, 0x8100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + xf_emit(ctx, 1, 4); /* 0000007f VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0x10); /* 7f/ff VIEW_VOLUME_CLIP_CTRL */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK0D7C */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK0F8C */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 1); /* 00000001 VIEWPORT_TRANSFORM_EN */ + xf_emit(ctx, 1, 0x8100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + xf_emit(ctx, 4, 0); /* ffffffff NOPERSPECTIVE_BITMAP */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1900 */ + xf_emit(ctx, 1, 0); /* 0000000f */ + if (dev_priv->chipset == 0x50) + xf_emit(ctx, 1, 0x3ff); /* 000003ff tesla UNK0D68 */ + else + xf_emit(ctx, 1, 0x7ff); /* 000007ff tesla UNK0D68 */ + xf_emit(ctx, 1, 0x80c14); /* 01ffffff SEMANTIC_COLOR */ + xf_emit(ctx, 1, 0); /* 00000001 VERTEX_TWO_SIDE_ENABLE */ + xf_emit(ctx, 0x30, 0); /* ffffffff VIEWPORT_SCALE: X0, Y0, Z0, X1, Y1, ... */ + xf_emit(ctx, 3, 0); /* f, 0, 0 */ + xf_emit(ctx, 3, 0); /* ffffffff last VIEWPORT_SCALE? */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 1); /* 00000001 VIEWPORT_TRANSFORM_EN */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1900 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1924 */ + xf_emit(ctx, 1, 0x10); /* 000000ff VIEW_VOLUME_CLIP_CTRL */ + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 0x30, 0); /* ffffffff VIEWPORT_TRANSLATE */ + xf_emit(ctx, 3, 0); /* f, 0, 0 */ + xf_emit(ctx, 3, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 2, 0x88); /* 000001ff tesla UNK19D8 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1924 */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 4); /* 0000000f CULL_MODE */ + xf_emit(ctx, 2, 0); /* 07ffffff SCREEN_SCISSOR */ + xf_emit(ctx, 2, 0); /* 00007fff WINDOW_OFFSET_XY */ + xf_emit(ctx, 1, 0); /* 00000003 WINDOW_ORIGIN */ + xf_emit(ctx, 0x10, 0); /* 00000001 SCISSOR_ENABLE */ + xf_emit(ctx, 1, 0); /* 0001ffff GP_BUILTIN_RESULT_EN */ + xf_emit(ctx, 1, 0x26); /* 000000ff SEMANTIC_LAYER */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1900 */ + xf_emit(ctx, 1, 0); /* 0000000f */ + xf_emit(ctx, 1, 0x3f800000); /* ffffffff LINE_WIDTH */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_STIPPLE_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_SMOOTH_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000007 MULTISAMPLE_SAMPLES_LOG2 */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 1, 0x1a); /* 0000001f POLYGON_MODE */ + xf_emit(ctx, 1, 0x10); /* 000000ff VIEW_VOLUME_CLIP_CTRL */ + if (dev_priv->chipset != 0x50) { + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 1, 0); /* 000003ff */ + } + xf_emit(ctx, 0x20, 0); /* 10xbits ffffffff, 3fffff. SCISSOR_* */ + xf_emit(ctx, 1, 0); /* f */ + xf_emit(ctx, 1, 0); /* 0? */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 003fffff */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 0x52); /* 000001ff SEMANTIC_PTSZ */ + xf_emit(ctx, 1, 0); /* 0001ffff GP_BUILTIN_RESULT_EN */ + xf_emit(ctx, 1, 0x26); /* 000000ff SEMANTIC_LAYER */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1900 */ + xf_emit(ctx, 1, 4); /* 0000007f VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0x1a); /* 0000001f POLYGON_MODE */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_SMOOTH_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_STIPPLE_ENABLE */ + xf_emit(ctx, 1, 0x00ffff00); /* 00ffffff LINE_STIPPLE_PATTERN */ + xf_emit(ctx, 1, 0); /* 0000000f */ +} + +static void +nv50_graph_construct_gene_zcull(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + /* end of strand 0 on pre-NVA0, beginning of strand 6 on NVAx */ + /* SEEK */ + xf_emit(ctx, 1, 0x3f); /* 0000003f UNK1590 */ + xf_emit(ctx, 1, 0); /* 00000001 ALPHA_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000007 MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 1, 0); /* 00000007 STENCIL_BACK_FUNC_FUNC */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_FUNC_MASK */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_FUNC_REF */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_MASK */ + xf_emit(ctx, 3, 0); /* 00000007 STENCIL_BACK_OP_FAIL, ZFAIL, ZPASS */ + xf_emit(ctx, 1, 2); /* 00000003 tesla UNK143C */ + xf_emit(ctx, 2, 0x04000000); /* 07ffffff tesla UNK0D6C */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 1, 0); /* 00000001 CLIPID_ENABLE */ + xf_emit(ctx, 2, 0); /* ffffffff DEPTH_BOUNDS */ + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 1, 0); /* 00000007 DEPTH_TEST_FUNC */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE_ENABLE */ + xf_emit(ctx, 1, 4); /* 0000000f CULL_MODE */ + xf_emit(ctx, 1, 0); /* 0000ffff */ + xf_emit(ctx, 1, 0); /* 00000001 UNK0FB0 */ + xf_emit(ctx, 1, 0); /* 00000001 POLYGON_STIPPLE_ENABLE */ + xf_emit(ctx, 1, 4); /* 00000007 FP_CONTROL */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 0001ffff GP_BUILTIN_RESULT_EN */ + xf_emit(ctx, 1, 0); /* 000000ff CLEAR_STENCIL */ + xf_emit(ctx, 1, 0); /* 00000007 STENCIL_FRONT_FUNC_FUNC */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_FUNC_MASK */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_FUNC_REF */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_MASK */ + xf_emit(ctx, 3, 0); /* 00000007 STENCIL_FRONT_OP_FAIL, ZFAIL, ZPASS */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_BACK_ENABLE */ + xf_emit(ctx, 1, 0); /* ffffffff CLEAR_DEPTH */ + xf_emit(ctx, 1, 0); /* 00000007 */ + if (dev_priv->chipset != 0x50) + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK1108 */ + xf_emit(ctx, 1, 0); /* 00000001 SAMPLECNT_ENABLE */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + xf_emit(ctx, 1, 0x1001); /* 00001fff ZETA_ARRAY_MODE */ + /* SEEK */ + xf_emit(ctx, 4, 0xffff); /* 0000ffff MSAA_MASK */ + xf_emit(ctx, 0x10, 0); /* 00000001 SCISSOR_ENABLE */ + xf_emit(ctx, 0x10, 0); /* ffffffff DEPTH_RANGE_NEAR */ + xf_emit(ctx, 0x10, 0x3f800000); /* ffffffff DEPTH_RANGE_FAR */ + xf_emit(ctx, 1, 0x10); /* 7f/ff/3ff VIEW_VOLUME_CLIP_CTRL */ + xf_emit(ctx, 1, 0); /* 00000001 VIEWPORT_CLIP_RECTS_EN */ + xf_emit(ctx, 1, 3); /* 00000003 FP_CTRL_UNK196C */ + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK1968 */ + if (dev_priv->chipset != 0x50) + xf_emit(ctx, 1, 0); /* 0fffffff tesla UNK1104 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK151C */ +} + +static void +nv50_graph_construct_gene_clipid(struct nouveau_grctx *ctx) +{ + /* middle of strand 0 on pre-NVA0 [after 24xx], middle of area 6 on NVAx */ + /* SEEK */ + xf_emit(ctx, 1, 0); /* 00000007 UNK0FB4 */ + /* SEEK */ + xf_emit(ctx, 4, 0); /* 07ffffff CLIPID_REGION_HORIZ */ + xf_emit(ctx, 4, 0); /* 07ffffff CLIPID_REGION_VERT */ + xf_emit(ctx, 2, 0); /* 07ffffff SCREEN_SCISSOR */ + xf_emit(ctx, 2, 0x04000000); /* 07ffffff UNK1508 */ + xf_emit(ctx, 1, 0); /* 00000001 CLIPID_ENABLE */ + xf_emit(ctx, 1, 0x80); /* 00003fff CLIPID_WIDTH */ + xf_emit(ctx, 1, 0); /* 000000ff CLIPID_ID */ + xf_emit(ctx, 1, 0); /* 000000ff CLIPID_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff CLIPID_ADDRESS_LOW */ + xf_emit(ctx, 1, 0x80); /* 00003fff CLIPID_HEIGHT */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_CLIPID */ +} + +static void +nv50_graph_construct_gene_unk24xx(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int i; + /* middle of strand 0 on pre-NVA0 [after m2mf], end of strand 2 on NVAx */ + /* SEEK */ + xf_emit(ctx, 0x33, 0); + /* SEEK */ + xf_emit(ctx, 2, 0); + /* SEEK */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 4); /* 0000007f VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + /* SEEK */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 4, 0); /* RO */ + xf_emit(ctx, 0xe10, 0); /* 190 * 9: 8*ffffffff, 7ff */ + xf_emit(ctx, 1, 0); /* 1ff */ + xf_emit(ctx, 8, 0); /* 0? */ + xf_emit(ctx, 9, 0); /* ffffffff, 7ff */ + + xf_emit(ctx, 4, 0); /* RO */ + xf_emit(ctx, 0xe10, 0); /* 190 * 9: 8*ffffffff, 7ff */ + xf_emit(ctx, 1, 0); /* 1ff */ + xf_emit(ctx, 8, 0); /* 0? */ + xf_emit(ctx, 9, 0); /* ffffffff, 7ff */ + } + else + { + xf_emit(ctx, 0xc, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 0xe10, 0); /* 190 * 9: 8*ffffffff, 7ff */ + xf_emit(ctx, 1, 0); /* 1ff */ + xf_emit(ctx, 8, 0); /* 0? */ + + /* SEEK */ + xf_emit(ctx, 0xc, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 0xe10, 0); /* 190 * 9: 8*ffffffff, 7ff */ + xf_emit(ctx, 1, 0); /* 1ff */ + xf_emit(ctx, 8, 0); /* 0? */ + } + /* SEEK */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 4); /* 0000007f VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0x8100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + if (dev_priv->chipset != 0x50) + xf_emit(ctx, 1, 3); /* 00000003 tesla UNK1100 */ + /* SEEK */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0x8100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + xf_emit(ctx, 1, 0); /* 0000000f VP_GP_BUILTIN_ATTR_EN */ + xf_emit(ctx, 1, 0x80c14); /* 01ffffff SEMANTIC_COLOR */ + xf_emit(ctx, 1, 1); /* 00000001 */ + /* SEEK */ + if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 2, 4); /* 000000ff */ + xf_emit(ctx, 1, 0x80c14); /* 01ffffff SEMANTIC_COLOR */ + xf_emit(ctx, 1, 0); /* 00000001 VERTEX_TWO_SIDE_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 POINT_SPRITE_ENABLE */ + xf_emit(ctx, 1, 0x8100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + xf_emit(ctx, 1, 0x27); /* 000000ff SEMANTIC_PRIM_ID */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0); /* 0000000f */ + xf_emit(ctx, 1, 1); /* 00000001 */ + for (i = 0; i < 10; i++) { + /* SEEK */ + xf_emit(ctx, 0x40, 0); /* ffffffff */ + xf_emit(ctx, 0x10, 0); /* 3, 0, 0.... */ + xf_emit(ctx, 0x10, 0); /* ffffffff */ + } + /* SEEK */ + xf_emit(ctx, 1, 0); /* 00000001 POINT_SPRITE_CTRL */ + xf_emit(ctx, 1, 1); /* 00000001 */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 4, 0); /* ffffffff NOPERSPECTIVE_BITMAP */ + xf_emit(ctx, 0x10, 0); /* 00ffffff POINT_COORD_REPLACE_MAP */ + xf_emit(ctx, 1, 0); /* 00000003 WINDOW_ORIGIN */ + xf_emit(ctx, 1, 0x8100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + if (dev_priv->chipset != 0x50) + xf_emit(ctx, 1, 0); /* 000003ff */ +} + +static void +nv50_graph_construct_gene_vfetch(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int acnt = 0x10, rep, i; + /* beginning of strand 1 on pre-NVA0, strand 3 on NVAx */ + if (IS_NVA3F(dev_priv->chipset)) + acnt = 0x20; + /* SEEK */ + if (dev_priv->chipset >= 0xa0) { + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK13A4 */ + xf_emit(ctx, 1, 1); /* 00000fff tesla UNK1318 */ + } + xf_emit(ctx, 1, 0); /* ffffffff VERTEX_BUFFER_FIRST */ + xf_emit(ctx, 1, 0); /* 00000001 PRIMITIVE_RESTART_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 UNK0DE8 */ + xf_emit(ctx, 1, 0); /* ffffffff PRIMITIVE_RESTART_INDEX */ + xf_emit(ctx, 1, 0xf); /* ffffffff VP_ATTR_EN */ + xf_emit(ctx, (acnt/8)-1, 0); /* ffffffff VP_ATTR_EN */ + xf_emit(ctx, acnt/8, 0); /* ffffffff VTX_ATR_MASK_UNK0DD0 */ + xf_emit(ctx, 1, 0); /* 0000000f VP_GP_BUILTIN_ATTR_EN */ + xf_emit(ctx, 1, 0x20); /* 0000ffff tesla UNK129C */ + xf_emit(ctx, 1, 0); /* 000000ff turing UNK370??? */ + xf_emit(ctx, 1, 0); /* 0000ffff turing USER_PARAM_COUNT */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + /* SEEK */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 0xb, 0); /* RO */ + else if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 0x9, 0); /* RO */ + else + xf_emit(ctx, 0x8, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 1, 0); /* 00000001 EDGE_FLAG */ + xf_emit(ctx, 1, 0); /* 00000001 PROVOKING_VERTEX_LAST */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0x1a); /* 0000001f POLYGON_MODE */ + /* SEEK */ + xf_emit(ctx, 0xc, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 1, 0); /* 7f/ff */ + xf_emit(ctx, 1, 4); /* 7f/ff VP_REG_ALLOC_RESULT */ + xf_emit(ctx, 1, 4); /* 7f/ff VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0); /* 0000000f VP_GP_BUILTIN_ATTR_EN */ + xf_emit(ctx, 1, 4); /* 000001ff UNK1A28 */ + xf_emit(ctx, 1, 8); /* 000001ff UNK0DF0 */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + if (dev_priv->chipset == 0x50) + xf_emit(ctx, 1, 0x3ff); /* 3ff tesla UNK0D68 */ + else + xf_emit(ctx, 1, 0x7ff); /* 7ff tesla UNK0D68 */ + if (dev_priv->chipset == 0xa8) + xf_emit(ctx, 1, 0x1e00); /* 7fff */ + /* SEEK */ + xf_emit(ctx, 0xc, 0); /* RO or close */ + /* SEEK */ + xf_emit(ctx, 1, 0xf); /* ffffffff VP_ATTR_EN */ + xf_emit(ctx, (acnt/8)-1, 0); /* ffffffff VP_ATTR_EN */ + xf_emit(ctx, 1, 0); /* 0000000f VP_GP_BUILTIN_ATTR_EN */ + if (dev_priv->chipset > 0x50 && dev_priv->chipset < 0xa0) + xf_emit(ctx, 2, 0); /* ffffffff */ + else + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK0FD8 */ + /* SEEK */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 0x10, 0); /* 0? */ + xf_emit(ctx, 2, 0); /* weird... */ + xf_emit(ctx, 2, 0); /* RO */ + } else { + xf_emit(ctx, 8, 0); /* 0? */ + xf_emit(ctx, 1, 0); /* weird... */ + xf_emit(ctx, 2, 0); /* RO */ + } + /* SEEK */ + xf_emit(ctx, 1, 0); /* ffffffff VB_ELEMENT_BASE */ + xf_emit(ctx, 1, 0); /* ffffffff UNK1438 */ + xf_emit(ctx, acnt, 0); /* 1 tesla UNK1000 */ + if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1118? */ + /* SEEK */ + xf_emit(ctx, acnt, 0); /* ffffffff VERTEX_ARRAY_UNK90C */ + xf_emit(ctx, 1, 0); /* f/1f */ + /* SEEK */ + xf_emit(ctx, acnt, 0); /* ffffffff VERTEX_ARRAY_UNK90C */ + xf_emit(ctx, 1, 0); /* f/1f */ + /* SEEK */ + xf_emit(ctx, acnt, 0); /* RO */ + xf_emit(ctx, 2, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK111C? */ + xf_emit(ctx, 1, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 1, 0); /* 000000ff UNK15F4_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff UNK15F4_ADDRESS_LOW */ + xf_emit(ctx, 1, 0); /* 000000ff UNK0F84_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff UNK0F84_ADDRESS_LOW */ + /* SEEK */ + xf_emit(ctx, acnt, 0); /* 00003fff VERTEX_ARRAY_ATTRIB_OFFSET */ + xf_emit(ctx, 3, 0); /* f/1f */ + /* SEEK */ + xf_emit(ctx, acnt, 0); /* 00000fff VERTEX_ARRAY_STRIDE */ + xf_emit(ctx, 3, 0); /* f/1f */ + /* SEEK */ + xf_emit(ctx, acnt, 0); /* ffffffff VERTEX_ARRAY_LOW */ + xf_emit(ctx, 3, 0); /* f/1f */ + /* SEEK */ + xf_emit(ctx, acnt, 0); /* 000000ff VERTEX_ARRAY_HIGH */ + xf_emit(ctx, 3, 0); /* f/1f */ + /* SEEK */ + xf_emit(ctx, acnt, 0); /* ffffffff VERTEX_LIMIT_LOW */ + xf_emit(ctx, 3, 0); /* f/1f */ + /* SEEK */ + xf_emit(ctx, acnt, 0); /* 000000ff VERTEX_LIMIT_HIGH */ + xf_emit(ctx, 3, 0); /* f/1f */ + /* SEEK */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, acnt, 0); /* f */ + xf_emit(ctx, 3, 0); /* f/1f */ + } + /* SEEK */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 2, 0); /* RO */ + else + xf_emit(ctx, 5, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 1, 0); /* ffff DMA_VTXBUF */ + /* SEEK */ + if (dev_priv->chipset < 0xa0) { + xf_emit(ctx, 0x41, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 0x11, 0); /* RO */ + } else if (!IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 0x50, 0); /* RO */ + else + xf_emit(ctx, 0x58, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 1, 0xf); /* ffffffff VP_ATTR_EN */ + xf_emit(ctx, (acnt/8)-1, 0); /* ffffffff VP_ATTR_EN */ + xf_emit(ctx, 1, 1); /* 1 UNK0DEC */ + /* SEEK */ + xf_emit(ctx, acnt*4, 0); /* ffffffff VTX_ATTR */ + xf_emit(ctx, 4, 0); /* f/1f, 0, 0, 0 */ + /* SEEK */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 0x1d, 0); /* RO */ + else + xf_emit(ctx, 0x16, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 1, 0xf); /* ffffffff VP_ATTR_EN */ + xf_emit(ctx, (acnt/8)-1, 0); /* ffffffff VP_ATTR_EN */ + /* SEEK */ + if (dev_priv->chipset < 0xa0) + xf_emit(ctx, 8, 0); /* RO */ + else if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 0xc, 0); /* RO */ + else + xf_emit(ctx, 7, 0); /* RO */ + /* SEEK */ + xf_emit(ctx, 0xa, 0); /* RO */ + if (dev_priv->chipset == 0xa0) + rep = 0xc; + else + rep = 4; + for (i = 0; i < rep; i++) { + /* SEEK */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 0x20, 0); /* ffffffff */ + xf_emit(ctx, 0x200, 0); /* ffffffff */ + xf_emit(ctx, 4, 0); /* 7f/ff, 0, 0, 0 */ + xf_emit(ctx, 4, 0); /* ffffffff */ + } + /* SEEK */ + xf_emit(ctx, 1, 0); /* 113/111 */ + xf_emit(ctx, 1, 0xf); /* ffffffff VP_ATTR_EN */ + xf_emit(ctx, (acnt/8)-1, 0); /* ffffffff VP_ATTR_EN */ + xf_emit(ctx, acnt/8, 0); /* ffffffff VTX_ATTR_MASK_UNK0DD0 */ + xf_emit(ctx, 1, 0); /* 0000000f VP_GP_BUILTIN_ATTR_EN */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + /* SEEK */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 7, 0); /* weird... */ + else + xf_emit(ctx, 5, 0); /* weird... */ +} + +static void +nv50_graph_construct_gene_eng2d(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + /* middle of strand 1 on pre-NVA0 [after vfetch], middle of strand 6 on NVAx */ + /* SEEK */ + xf_emit(ctx, 2, 0); /* 0001ffff CLIP_X, CLIP_Y */ + xf_emit(ctx, 2, 0); /* 0000ffff CLIP_W, CLIP_H */ + xf_emit(ctx, 1, 0); /* 00000001 CLIP_ENABLE */ + if (dev_priv->chipset < 0xa0) { + /* this is useless on everything but the original NV50, + * guess they forgot to nuke it. Or just didn't bother. */ + xf_emit(ctx, 2, 0); /* 0000ffff IFC_CLIP_X, Y */ + xf_emit(ctx, 2, 1); /* 0000ffff IFC_CLIP_W, H */ + xf_emit(ctx, 1, 0); /* 00000001 IFC_CLIP_ENABLE */ + } + xf_emit(ctx, 1, 1); /* 00000001 DST_LINEAR */ + xf_emit(ctx, 1, 0x100); /* 0001ffff DST_WIDTH */ + xf_emit(ctx, 1, 0x100); /* 0001ffff DST_HEIGHT */ + xf_emit(ctx, 1, 0x11); /* 3f[NV50]/7f[NV84+] DST_FORMAT */ + xf_emit(ctx, 1, 0); /* 0001ffff DRAW_POINT_X */ + xf_emit(ctx, 1, 8); /* 0000000f DRAW_UNK58C */ + xf_emit(ctx, 1, 0); /* 000fffff SIFC_DST_X_FRACT */ + xf_emit(ctx, 1, 0); /* 0001ffff SIFC_DST_X_INT */ + xf_emit(ctx, 1, 0); /* 000fffff SIFC_DST_Y_FRACT */ + xf_emit(ctx, 1, 0); /* 0001ffff SIFC_DST_Y_INT */ + xf_emit(ctx, 1, 0); /* 000fffff SIFC_DX_DU_FRACT */ + xf_emit(ctx, 1, 1); /* 0001ffff SIFC_DX_DU_INT */ + xf_emit(ctx, 1, 0); /* 000fffff SIFC_DY_DV_FRACT */ + xf_emit(ctx, 1, 1); /* 0001ffff SIFC_DY_DV_INT */ + xf_emit(ctx, 1, 1); /* 0000ffff SIFC_WIDTH */ + xf_emit(ctx, 1, 1); /* 0000ffff SIFC_HEIGHT */ + xf_emit(ctx, 1, 0xcf); /* 000000ff SIFC_FORMAT */ + xf_emit(ctx, 1, 2); /* 00000003 SIFC_BITMAP_UNK808 */ + xf_emit(ctx, 1, 0); /* 00000003 SIFC_BITMAP_LINE_PACK_MODE */ + xf_emit(ctx, 1, 0); /* 00000001 SIFC_BITMAP_LSB_FIRST */ + xf_emit(ctx, 1, 0); /* 00000001 SIFC_BITMAP_ENABLE */ + xf_emit(ctx, 1, 0); /* 0000ffff BLIT_DST_X */ + xf_emit(ctx, 1, 0); /* 0000ffff BLIT_DST_Y */ + xf_emit(ctx, 1, 0); /* 000fffff BLIT_DU_DX_FRACT */ + xf_emit(ctx, 1, 1); /* 0001ffff BLIT_DU_DX_INT */ + xf_emit(ctx, 1, 0); /* 000fffff BLIT_DV_DY_FRACT */ + xf_emit(ctx, 1, 1); /* 0001ffff BLIT_DV_DY_INT */ + xf_emit(ctx, 1, 1); /* 0000ffff BLIT_DST_W */ + xf_emit(ctx, 1, 1); /* 0000ffff BLIT_DST_H */ + xf_emit(ctx, 1, 0); /* 000fffff BLIT_SRC_X_FRACT */ + xf_emit(ctx, 1, 0); /* 0001ffff BLIT_SRC_X_INT */ + xf_emit(ctx, 1, 0); /* 000fffff BLIT_SRC_Y_FRACT */ + xf_emit(ctx, 1, 0); /* 00000001 UNK888 */ + xf_emit(ctx, 1, 4); /* 0000003f UNK884 */ + xf_emit(ctx, 1, 0); /* 00000007 UNK880 */ + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK0FB8 */ + xf_emit(ctx, 1, 0x15); /* 000000ff tesla UNK128C */ + xf_emit(ctx, 2, 0); /* 00000007, ffff0ff3 */ + xf_emit(ctx, 1, 0); /* 00000001 UNK260 */ + xf_emit(ctx, 1, 0x4444480); /* 1fffffff UNK870 */ + /* SEEK */ + xf_emit(ctx, 0x10, 0); + /* SEEK */ + xf_emit(ctx, 0x27, 0); +} + +static void +nv50_graph_construct_gene_csched(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + /* middle of strand 1 on pre-NVA0 [after eng2d], middle of strand 0 on NVAx */ + /* SEEK */ + xf_emit(ctx, 2, 0); /* 00007fff WINDOW_OFFSET_XY... what is it doing here??? */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1924 */ + xf_emit(ctx, 1, 0); /* 00000003 WINDOW_ORIGIN */ + xf_emit(ctx, 1, 0x8100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + xf_emit(ctx, 1, 0); /* 000003ff */ + /* SEEK */ + xf_emit(ctx, 1, 0); /* ffffffff turing UNK364 */ + xf_emit(ctx, 1, 0); /* 0000000f turing UNK36C */ + xf_emit(ctx, 1, 0); /* 0000ffff USER_PARAM_COUNT */ + xf_emit(ctx, 1, 0x100); /* 00ffffff turing UNK384 */ + xf_emit(ctx, 1, 0); /* 0000000f turing UNK2A0 */ + xf_emit(ctx, 1, 0); /* 0000ffff GRIDID */ + xf_emit(ctx, 1, 0x10001); /* ffffffff GRIDDIM_XY */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 1, 0x10001); /* ffffffff BLOCKDIM_XY */ + xf_emit(ctx, 1, 1); /* 0000ffff BLOCKDIM_Z */ + xf_emit(ctx, 1, 0x10001); /* 00ffffff BLOCK_ALLOC */ + xf_emit(ctx, 1, 1); /* 00000001 LANES32 */ + xf_emit(ctx, 1, 4); /* 000000ff FP_REG_ALLOC_TEMP */ + xf_emit(ctx, 1, 2); /* 00000003 REG_MODE */ + /* SEEK */ + xf_emit(ctx, 0x40, 0); /* ffffffff USER_PARAM */ + switch (dev_priv->chipset) { + case 0x50: + case 0x92: + xf_emit(ctx, 8, 0); /* 7, 0, 0, 0, ... */ + xf_emit(ctx, 0x80, 0); /* fff */ + xf_emit(ctx, 2, 0); /* ff, fff */ + xf_emit(ctx, 0x10*2, 0); /* ffffffff, 1f */ + break; + case 0x84: + xf_emit(ctx, 8, 0); /* 7, 0, 0, 0, ... */ + xf_emit(ctx, 0x60, 0); /* fff */ + xf_emit(ctx, 2, 0); /* ff, fff */ + xf_emit(ctx, 0xc*2, 0); /* ffffffff, 1f */ + break; + case 0x94: + case 0x96: + xf_emit(ctx, 8, 0); /* 7, 0, 0, 0, ... */ + xf_emit(ctx, 0x40, 0); /* fff */ + xf_emit(ctx, 2, 0); /* ff, fff */ + xf_emit(ctx, 8*2, 0); /* ffffffff, 1f */ + break; + case 0x86: + case 0x98: + xf_emit(ctx, 4, 0); /* f, 0, 0, 0 */ + xf_emit(ctx, 0x10, 0); /* fff */ + xf_emit(ctx, 2, 0); /* ff, fff */ + xf_emit(ctx, 2*2, 0); /* ffffffff, 1f */ + break; + case 0xa0: + xf_emit(ctx, 8, 0); /* 7, 0, 0, 0, ... */ + xf_emit(ctx, 0xf0, 0); /* fff */ + xf_emit(ctx, 2, 0); /* ff, fff */ + xf_emit(ctx, 0x1e*2, 0); /* ffffffff, 1f */ + break; + case 0xa3: + xf_emit(ctx, 8, 0); /* 7, 0, 0, 0, ... */ + xf_emit(ctx, 0x60, 0); /* fff */ + xf_emit(ctx, 2, 0); /* ff, fff */ + xf_emit(ctx, 0xc*2, 0); /* ffffffff, 1f */ + break; + case 0xa5: + case 0xaf: + xf_emit(ctx, 8, 0); /* 7, 0, 0, 0, ... */ + xf_emit(ctx, 0x30, 0); /* fff */ + xf_emit(ctx, 2, 0); /* ff, fff */ + xf_emit(ctx, 6*2, 0); /* ffffffff, 1f */ + break; + case 0xaa: + xf_emit(ctx, 0x12, 0); + break; + case 0xa8: + case 0xac: + xf_emit(ctx, 4, 0); /* f, 0, 0, 0 */ + xf_emit(ctx, 0x10, 0); /* fff */ + xf_emit(ctx, 2, 0); /* ff, fff */ + xf_emit(ctx, 2*2, 0); /* ffffffff, 1f */ + break; + } + xf_emit(ctx, 1, 0); /* 0000000f */ + xf_emit(ctx, 1, 0); /* 00000000 */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 0000001f */ + xf_emit(ctx, 4, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 00000003 turing UNK35C */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 4, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 00000003 turing UNK35C */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 000000ff */ +} + +static void +nv50_graph_construct_gene_unk1cxx(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + xf_emit(ctx, 2, 0); /* 00007fff WINDOW_OFFSET_XY */ + xf_emit(ctx, 1, 0x3f800000); /* ffffffff LINE_WIDTH */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_SMOOTH_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1658 */ + xf_emit(ctx, 1, 0); /* 00000001 POLYGON_SMOOTH_ENABLE */ + xf_emit(ctx, 3, 0); /* 00000001 POLYGON_OFFSET_*_ENABLE */ + xf_emit(ctx, 1, 4); /* 0000000f CULL_MODE */ + xf_emit(ctx, 1, 0x1a); /* 0000001f POLYGON_MODE */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 0); /* 00000001 POINT_SPRITE_ENABLE */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK165C */ + xf_emit(ctx, 0x10, 0); /* 00000001 SCISSOR_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_STIPPLE_ENABLE */ + xf_emit(ctx, 1, 0x00ffff00); /* 00ffffff LINE_STIPPLE_PATTERN */ + xf_emit(ctx, 1, 0); /* ffffffff POLYGON_OFFSET_UNITS */ + xf_emit(ctx, 1, 0); /* ffffffff POLYGON_OFFSET_FACTOR */ + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK1668 */ + xf_emit(ctx, 2, 0); /* 07ffffff SCREEN_SCISSOR */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1900 */ + xf_emit(ctx, 1, 0xf); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 7, 0); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 1, 0x0fac6881); /* 0fffffff RT_CONTROL */ + xf_emit(ctx, 1, 0x11); /* 0000007f RT_FORMAT */ + xf_emit(ctx, 7, 0); /* 0000007f RT_FORMAT */ + xf_emit(ctx, 8, 0); /* 00000001 RT_HORIZ_LINEAR */ + xf_emit(ctx, 1, 4); /* 00000007 FP_CONTROL */ + xf_emit(ctx, 1, 0); /* 00000001 ALPHA_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000007 ALPHA_TEST_FUNC */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 3); /* 00000003 UNK16B4 */ + else if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 1, 1); /* 00000001 UNK16B4 */ + xf_emit(ctx, 1, 0); /* 00000003 MULTISAMPLE_CTRL */ + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK0F90 */ + xf_emit(ctx, 1, 2); /* 00000003 tesla UNK143C */ + xf_emit(ctx, 2, 0x04000000); /* 07ffffff tesla UNK0D6C */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_MASK */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 SAMPLECNT_ENABLE */ + xf_emit(ctx, 1, 5); /* 0000000f UNK1408 */ + xf_emit(ctx, 1, 0x52); /* 000001ff SEMANTIC_PTSZ */ + xf_emit(ctx, 1, 0); /* ffffffff POINT_SIZE */ + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 1, 0); /* 00000007 tesla UNK0FB4 */ + if (dev_priv->chipset != 0x50) { + xf_emit(ctx, 1, 0); /* 3ff */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK1110 */ + } + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK1928 */ + xf_emit(ctx, 0x10, 0); /* ffffffff DEPTH_RANGE_NEAR */ + xf_emit(ctx, 0x10, 0x3f800000); /* ffffffff DEPTH_RANGE_FAR */ + xf_emit(ctx, 1, 0x10); /* 000000ff VIEW_VOLUME_CLIP_CTRL */ + xf_emit(ctx, 0x20, 0); /* 07ffffff VIEWPORT_HORIZ, then VIEWPORT_VERT. (W&0x3fff)<<13 | (X&0x1fff). */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK187C */ + xf_emit(ctx, 1, 0); /* 00000003 WINDOW_ORIGIN */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_BACK_ENABLE */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_MASK */ + xf_emit(ctx, 1, 0x8100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + xf_emit(ctx, 1, 5); /* 0000000f tesla UNK1220 */ + xf_emit(ctx, 1, 0); /* 00000007 MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 000000ff tesla UNK1A20 */ + xf_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 VERTEX_TWO_SIDE_ENABLE */ + xf_emit(ctx, 4, 0xffff); /* 0000ffff MSAA_MASK */ + if (dev_priv->chipset != 0x50) + xf_emit(ctx, 1, 3); /* 00000003 tesla UNK1100 */ + if (dev_priv->chipset < 0xa0) + xf_emit(ctx, 0x1c, 0); /* RO */ + else if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 0x9, 0); + xf_emit(ctx, 1, 0); /* 00000001 UNK1534 */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_SMOOTH_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_STIPPLE_ENABLE */ + xf_emit(ctx, 1, 0x00ffff00); /* 00ffffff LINE_STIPPLE_PATTERN */ + xf_emit(ctx, 1, 0x1a); /* 0000001f POLYGON_MODE */ + xf_emit(ctx, 1, 0); /* 00000003 WINDOW_ORIGIN */ + if (dev_priv->chipset != 0x50) { + xf_emit(ctx, 1, 3); /* 00000003 tesla UNK1100 */ + xf_emit(ctx, 1, 0); /* 3ff */ + } + /* XXX: the following block could belong either to unk1cxx, or + * to STRMOUT. Rather hard to tell. */ + if (dev_priv->chipset < 0xa0) + xf_emit(ctx, 0x25, 0); + else + xf_emit(ctx, 0x3b, 0); +} + +static void +nv50_graph_construct_gene_strmout(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + xf_emit(ctx, 1, 0x102); /* 0000ffff STRMOUT_BUFFER_CTRL */ + xf_emit(ctx, 1, 0); /* ffffffff STRMOUT_PRIMITIVE_COUNT */ + xf_emit(ctx, 4, 4); /* 000000ff STRMOUT_NUM_ATTRIBS */ + if (dev_priv->chipset >= 0xa0) { + xf_emit(ctx, 4, 0); /* ffffffff UNK1A8C */ + xf_emit(ctx, 4, 0); /* ffffffff UNK1780 */ + } + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 4); /* 0000007f VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + if (dev_priv->chipset == 0x50) + xf_emit(ctx, 1, 0x3ff); /* 000003ff tesla UNK0D68 */ + else + xf_emit(ctx, 1, 0x7ff); /* 000007ff tesla UNK0D68 */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + /* SEEK */ + xf_emit(ctx, 1, 0x102); /* 0000ffff STRMOUT_BUFFER_CTRL */ + xf_emit(ctx, 1, 0); /* ffffffff STRMOUT_PRIMITIVE_COUNT */ + xf_emit(ctx, 4, 0); /* 000000ff STRMOUT_ADDRESS_HIGH */ + xf_emit(ctx, 4, 0); /* ffffffff STRMOUT_ADDRESS_LOW */ + xf_emit(ctx, 4, 4); /* 000000ff STRMOUT_NUM_ATTRIBS */ + if (dev_priv->chipset >= 0xa0) { + xf_emit(ctx, 4, 0); /* ffffffff UNK1A8C */ + xf_emit(ctx, 4, 0); /* ffffffff UNK1780 */ + } + xf_emit(ctx, 1, 0); /* 0000ffff DMA_STRMOUT */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_QUERY */ + xf_emit(ctx, 1, 0); /* 000000ff QUERY_ADDRESS_HIGH */ + xf_emit(ctx, 2, 0); /* ffffffff QUERY_ADDRESS_LOW QUERY_COUNTER */ + xf_emit(ctx, 2, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + /* SEEK */ + xf_emit(ctx, 0x20, 0); /* ffffffff STRMOUT_MAP */ + xf_emit(ctx, 1, 0); /* 0000000f */ + xf_emit(ctx, 1, 0); /* 00000000? */ + xf_emit(ctx, 2, 0); /* ffffffff */ +} + +static void +nv50_graph_construct_gene_ropm1(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + xf_emit(ctx, 1, 0x4e3bfdf); /* ffffffff UNK0D64 */ + xf_emit(ctx, 1, 0x4e3bfdf); /* ffffffff UNK0DF4 */ + xf_emit(ctx, 1, 0); /* 00000007 */ + xf_emit(ctx, 1, 0); /* 000003ff */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 0x11); /* 000000ff tesla UNK1968 */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ +} + +static void +nv50_graph_construct_gene_ropm2(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + /* SEEK */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_QUERY */ + xf_emit(ctx, 1, 0x0fac6881); /* 0fffffff RT_CONTROL */ + xf_emit(ctx, 2, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 000000ff QUERY_ADDRESS_HIGH */ + xf_emit(ctx, 2, 0); /* ffffffff QUERY_ADDRESS_LOW, COUNTER */ + xf_emit(ctx, 1, 0); /* 00000001 SAMPLECNT_ENABLE */ + xf_emit(ctx, 1, 0); /* 7 */ + /* SEEK */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_QUERY */ + xf_emit(ctx, 1, 0); /* 000000ff QUERY_ADDRESS_HIGH */ + xf_emit(ctx, 2, 0); /* ffffffff QUERY_ADDRESS_LOW, COUNTER */ + xf_emit(ctx, 1, 0x4e3bfdf); /* ffffffff UNK0D64 */ + xf_emit(ctx, 1, 0x4e3bfdf); /* ffffffff UNK0DF4 */ + xf_emit(ctx, 1, 0); /* 00000001 eng2d UNK260 */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + xf_emit(ctx, 1, 0); /* 00000007 */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 0x11); /* 000000ff tesla UNK1968 */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ +} + +static void +nv50_graph_construct_gene_ropc(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int magic2; + if (dev_priv->chipset == 0x50) { + magic2 = 0x00003e60; + } else if (!IS_NVA3F(dev_priv->chipset)) { + magic2 = 0x001ffe67; + } else { + magic2 = 0x00087e67; + } + xf_emit(ctx, 1, 0); /* f/7 MUTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 1, 0); /* 00000007 STENCIL_BACK_FUNC_FUNC */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_FUNC_MASK */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_MASK */ + xf_emit(ctx, 3, 0); /* 00000007 STENCIL_BACK_OP_FAIL, ZFAIL, ZPASS */ + xf_emit(ctx, 1, 2); /* 00000003 tesla UNK143C */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 1, magic2); /* 001fffff tesla UNK0F78 */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_BOUNDS_EN */ + xf_emit(ctx, 1, 0); /* 00000007 DEPTH_TEST_FUNC */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE_ENABLE */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + xf_emit(ctx, 1, 0); /* 00000007 STENCIL_FRONT_FUNC_FUNC */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_FUNC_MASK */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_MASK */ + xf_emit(ctx, 3, 0); /* 00000007 STENCIL_FRONT_OP_FAIL, ZFAIL, ZPASS */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + if (dev_priv->chipset >= 0xa0 && !IS_NVAAF(dev_priv->chipset)) + xf_emit(ctx, 1, 0x15); /* 000000ff */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_BACK_ENABLE */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK15B4 */ + xf_emit(ctx, 1, 0x10); /* 3ff/ff VIEW_VOLUME_CLIP_CTRL */ + xf_emit(ctx, 1, 0); /* ffffffff CLEAR_DEPTH */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ + if (dev_priv->chipset == 0x86 || dev_priv->chipset == 0x92 || dev_priv->chipset == 0x98 || dev_priv->chipset >= 0xa0) { + xf_emit(ctx, 3, 0); /* ff, ffffffff, ffffffff */ + xf_emit(ctx, 1, 4); /* 7 */ + xf_emit(ctx, 1, 0x400); /* fffffff */ + xf_emit(ctx, 1, 0x300); /* ffff */ + xf_emit(ctx, 1, 0x1001); /* 1fff */ + if (dev_priv->chipset != 0xa0) { + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 0); /* 0000000f UNK15C8 */ + else + xf_emit(ctx, 1, 0x15); /* ff */ + } + } + xf_emit(ctx, 1, 0); /* 00000007 MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 1, 0); /* 00000007 STENCIL_BACK_FUNC_FUNC */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_FUNC_MASK */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 1, 2); /* 00000003 tesla UNK143C */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_BOUNDS_EN */ + xf_emit(ctx, 1, 0); /* 00000007 DEPTH_TEST_FUNC */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000007 STENCIL_FRONT_FUNC_FUNC */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_FUNC_MASK */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_BACK_ENABLE */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK15B4 */ + xf_emit(ctx, 1, 0x10); /* 7f/ff VIEW_VOLUME_CLIP_CTRL */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1900 */ + xf_emit(ctx, 1, 0); /* 00000007 STENCIL_BACK_FUNC_FUNC */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_FUNC_MASK */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_FUNC_REF */ + xf_emit(ctx, 2, 0); /* ffffffff DEPTH_BOUNDS */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_BOUNDS_EN */ + xf_emit(ctx, 1, 0); /* 00000007 DEPTH_TEST_FUNC */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE_ENABLE */ + xf_emit(ctx, 1, 0); /* 0000000f */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK0FB0 */ + xf_emit(ctx, 1, 0); /* 00000007 STENCIL_FRONT_FUNC_FUNC */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_FUNC_MASK */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_FUNC_REF */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_BACK_ENABLE */ + xf_emit(ctx, 1, 0x10); /* 7f/ff VIEW_VOLUME_CLIP_CTRL */ + xf_emit(ctx, 0x10, 0); /* ffffffff DEPTH_RANGE_NEAR */ + xf_emit(ctx, 0x10, 0x3f800000); /* ffffffff DEPTH_RANGE_FAR */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 0); /* 00000007 MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000007 STENCIL_BACK_FUNC_FUNC */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_FUNC_MASK */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_FUNC_REF */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_MASK */ + xf_emit(ctx, 3, 0); /* 00000007 STENCIL_BACK_OP_FAIL, ZFAIL, ZPASS */ + xf_emit(ctx, 2, 0); /* ffffffff DEPTH_BOUNDS */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_BOUNDS_EN */ + xf_emit(ctx, 1, 0); /* 00000007 DEPTH_TEST_FUNC */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE_ENABLE */ + xf_emit(ctx, 1, 0); /* 000000ff CLEAR_STENCIL */ + xf_emit(ctx, 1, 0); /* 00000007 STENCIL_FRONT_FUNC_FUNC */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_FUNC_MASK */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_FUNC_REF */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_MASK */ + xf_emit(ctx, 3, 0); /* 00000007 STENCIL_FRONT_OP_FAIL, ZFAIL, ZPASS */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_BACK_ENABLE */ + xf_emit(ctx, 1, 0x10); /* 7f/ff VIEW_VOLUME_CLIP_CTRL */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 0x3f); /* 0000003f UNK1590 */ + xf_emit(ctx, 1, 0); /* 00000007 MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 2, 0); /* ffff0ff3, ffff */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK0FB0 */ + xf_emit(ctx, 1, 0); /* 0001ffff GP_BUILTIN_RESULT_EN */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK15B4 */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + xf_emit(ctx, 1, 0); /* ffffffff CLEAR_DEPTH */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK19CC */ + if (dev_priv->chipset >= 0xa0) { + xf_emit(ctx, 2, 0); + xf_emit(ctx, 1, 0x1001); + xf_emit(ctx, 0xb, 0); + } else { + xf_emit(ctx, 1, 0); /* 00000007 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 1, 0); /* 00000007 MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 8, 0); /* 00000001 BLEND_ENABLE */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + } + xf_emit(ctx, 1, 0x11); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 7, 0); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 1, 0xf); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 7, 0); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 1, 0x11); /* 3f/7f */ + xf_emit(ctx, 1, 0); /* 00000001 LOGIC_OP_ENABLE */ + if (dev_priv->chipset != 0x50) { + xf_emit(ctx, 1, 0); /* 0000000f LOGIC_OP */ + xf_emit(ctx, 1, 0); /* 000000ff */ + } + xf_emit(ctx, 1, 0); /* 00000007 OPERATION */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + xf_emit(ctx, 1, 0); /* 00000003 UNK0F90 */ + xf_emit(ctx, 2, 1); /* 00000007 BLEND_EQUATION_RGB, ALPHA */ + xf_emit(ctx, 1, 1); /* 00000001 UNK133C */ + xf_emit(ctx, 1, 2); /* 0000001f BLEND_FUNC_SRC_RGB */ + xf_emit(ctx, 1, 1); /* 0000001f BLEND_FUNC_DST_RGB */ + xf_emit(ctx, 1, 2); /* 0000001f BLEND_FUNC_SRC_ALPHA */ + xf_emit(ctx, 1, 1); /* 0000001f BLEND_FUNC_DST_ALPHA */ + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 1, magic2); /* 001fffff tesla UNK0F78 */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ + xf_emit(ctx, 1, 0x0fac6881); /* 0fffffff RT_CONTROL */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK12E4 */ + xf_emit(ctx, 8, 1); /* 00000007 IBLEND_EQUATION_RGB */ + xf_emit(ctx, 8, 1); /* 00000007 IBLEND_EQUATION_ALPHA */ + xf_emit(ctx, 8, 1); /* 00000001 IBLEND_UNK00 */ + xf_emit(ctx, 8, 2); /* 0000001f IBLEND_FUNC_SRC_RGB */ + xf_emit(ctx, 8, 1); /* 0000001f IBLEND_FUNC_DST_RGB */ + xf_emit(ctx, 8, 2); /* 0000001f IBLEND_FUNC_SRC_ALPHA */ + xf_emit(ctx, 8, 1); /* 0000001f IBLEND_FUNC_DST_ALPHA */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1140 */ + xf_emit(ctx, 2, 0); /* 00000001 */ + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + xf_emit(ctx, 1, 0); /* 0000000f */ + xf_emit(ctx, 1, 0); /* 00000003 */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 2, 0); /* 00000001 */ + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 1, 0); /* 000003ff */ + } else if (dev_priv->chipset >= 0xa0) { + xf_emit(ctx, 2, 0); /* 00000001 */ + xf_emit(ctx, 1, 0); /* 00000007 */ + xf_emit(ctx, 1, 0); /* 00000003 */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 2, 0); /* 00000001 */ + } else { + xf_emit(ctx, 1, 0); /* 00000007 MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK1430 */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ + } + xf_emit(ctx, 4, 0); /* ffffffff CLEAR_COLOR */ + xf_emit(ctx, 4, 0); /* ffffffff BLEND_COLOR A R G B */ + xf_emit(ctx, 1, 0); /* 00000fff eng2d UNK2B0 */ + if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 2, 0); /* 00000001 */ + xf_emit(ctx, 1, 0); /* 000003ff */ + xf_emit(ctx, 8, 0); /* 00000001 BLEND_ENABLE */ + xf_emit(ctx, 1, 1); /* 00000001 UNK133C */ + xf_emit(ctx, 1, 2); /* 0000001f BLEND_FUNC_SRC_RGB */ + xf_emit(ctx, 1, 1); /* 0000001f BLEND_FUNC_DST_RGB */ + xf_emit(ctx, 1, 1); /* 00000007 BLEND_EQUATION_RGB */ + xf_emit(ctx, 1, 2); /* 0000001f BLEND_FUNC_SRC_ALPHA */ + xf_emit(ctx, 1, 1); /* 0000001f BLEND_FUNC_DST_ALPHA */ + xf_emit(ctx, 1, 1); /* 00000007 BLEND_EQUATION_ALPHA */ + xf_emit(ctx, 1, 0); /* 00000001 UNK19C0 */ + xf_emit(ctx, 1, 0); /* 00000001 LOGIC_OP_ENABLE */ + xf_emit(ctx, 1, 0); /* 0000000f LOGIC_OP */ + if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 1, 0); /* 00000001 UNK12E4? NVA3+ only? */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 8, 1); /* 00000001 IBLEND_UNK00 */ + xf_emit(ctx, 8, 1); /* 00000007 IBLEND_EQUATION_RGB */ + xf_emit(ctx, 8, 2); /* 0000001f IBLEND_FUNC_SRC_RGB */ + xf_emit(ctx, 8, 1); /* 0000001f IBLEND_FUNC_DST_RGB */ + xf_emit(ctx, 8, 1); /* 00000007 IBLEND_EQUATION_ALPHA */ + xf_emit(ctx, 8, 2); /* 0000001f IBLEND_FUNC_SRC_ALPHA */ + xf_emit(ctx, 8, 1); /* 0000001f IBLEND_FUNC_DST_ALPHA */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK15C4 */ + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1140 */ + } + xf_emit(ctx, 1, 0x11); /* 3f/7f DST_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 DST_LINEAR */ + xf_emit(ctx, 1, 0); /* 00000007 PATTERN_COLOR_FORMAT */ + xf_emit(ctx, 2, 0); /* ffffffff PATTERN_MONO_COLOR */ + xf_emit(ctx, 1, 0); /* 00000001 PATTERN_MONO_FORMAT */ + xf_emit(ctx, 2, 0); /* ffffffff PATTERN_MONO_BITMAP */ + xf_emit(ctx, 1, 0); /* 00000003 PATTERN_SELECT */ + xf_emit(ctx, 1, 0); /* 000000ff ROP */ + xf_emit(ctx, 1, 0); /* ffffffff BETA1 */ + xf_emit(ctx, 1, 0); /* ffffffff BETA4 */ + xf_emit(ctx, 1, 0); /* 00000007 OPERATION */ + xf_emit(ctx, 0x50, 0); /* 10x ffffff, ffffff, ffffff, ffffff, 3 PATTERN */ +} + +static void +nv50_graph_construct_xfer_unk84xx(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int magic3; + switch (dev_priv->chipset) { + case 0x50: + magic3 = 0x1000; + break; + case 0x86: + case 0x98: + case 0xa8: + case 0xaa: + case 0xac: + case 0xaf: + magic3 = 0x1e00; + break; + default: + magic3 = 0; + } + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 4); /* 7f/ff[NVA0+] VP_REG_ALLOC_RESULT */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 0); /* 111/113[NVA0+] */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 0x1f, 0); /* ffffffff */ + else if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 0x0f, 0); /* ffffffff */ + else + xf_emit(ctx, 0x10, 0); /* fffffff VP_RESULT_MAP_1 up */ + xf_emit(ctx, 2, 0); /* f/1f[NVA3], fffffff/ffffffff[NVA0+] */ + xf_emit(ctx, 1, 4); /* 7f/ff VP_REG_ALLOC_RESULT */ + xf_emit(ctx, 1, 4); /* 7f/ff VP_RESULT_MAP_SIZE */ + if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 1, 0x03020100); /* ffffffff */ + else + xf_emit(ctx, 1, 0x00608080); /* fffffff VP_RESULT_MAP_0 */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 2, 0); /* 111/113, 7f/ff */ + xf_emit(ctx, 1, 4); /* 7f/ff VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 4); /* 000000ff GP_REG_ALLOC_RESULT */ + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0x80); /* 0000ffff GP_VERTEX_OUTPUT_COUNT */ + if (magic3) + xf_emit(ctx, 1, magic3); /* 00007fff tesla UNK141C */ + xf_emit(ctx, 1, 4); /* 7f/ff VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 0); /* 111/113 */ + xf_emit(ctx, 0x1f, 0); /* ffffffff GP_RESULT_MAP_1 up */ + xf_emit(ctx, 1, 0); /* 0000001f */ + xf_emit(ctx, 1, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 4); /* 000000ff GP_REG_ALLOC_RESULT */ + xf_emit(ctx, 1, 0x80); /* 0000ffff GP_VERTEX_OUTPUT_COUNT */ + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0x03020100); /* ffffffff GP_RESULT_MAP_0 */ + xf_emit(ctx, 1, 3); /* 00000003 GP_OUTPUT_PRIMITIVE_TYPE */ + if (magic3) + xf_emit(ctx, 1, magic3); /* 7fff tesla UNK141C */ + xf_emit(ctx, 1, 4); /* 7f/ff VP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 0); /* 00000001 PROVOKING_VERTEX_LAST */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 0); /* 111/113 */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 3); /* 00000003 GP_OUTPUT_PRIMITIVE_TYPE */ + xf_emit(ctx, 1, 0); /* 00000001 PROVOKING_VERTEX_LAST */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK13A0 */ + xf_emit(ctx, 1, 4); /* 7f/ff VP_REG_ALLOC_RESULT */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + xf_emit(ctx, 1, 0); /* 111/113 */ + if (dev_priv->chipset == 0x94 || dev_priv->chipset == 0x96) + xf_emit(ctx, 0x1020, 0); /* 4 x (0x400 x 0xffffffff, ff, 0, 0, 0, 4 x ffffffff) */ + else if (dev_priv->chipset < 0xa0) + xf_emit(ctx, 0xa20, 0); /* 4 x (0x280 x 0xffffffff, ff, 0, 0, 0, 4 x ffffffff) */ + else if (!IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 0x210, 0); /* ffffffff */ + else + xf_emit(ctx, 0x410, 0); /* ffffffff */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 4); /* 000000ff GP_RESULT_MAP_SIZE */ + xf_emit(ctx, 1, 3); /* 00000003 GP_OUTPUT_PRIMITIVE_TYPE */ + xf_emit(ctx, 1, 0); /* 00000001 PROVOKING_VERTEX_LAST */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ +} + +static void +nv50_graph_construct_xfer_tprop(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int magic1, magic2; + if (dev_priv->chipset == 0x50) { + magic1 = 0x3ff; + magic2 = 0x00003e60; + } else if (!IS_NVA3F(dev_priv->chipset)) { + magic1 = 0x7ff; + magic2 = 0x001ffe67; + } else { + magic1 = 0x7ff; + magic2 = 0x00087e67; + } + xf_emit(ctx, 1, 0); /* 00000007 ALPHA_TEST_FUNC */ + xf_emit(ctx, 1, 0); /* ffffffff ALPHA_TEST_REF */ + xf_emit(ctx, 1, 0); /* 00000001 ALPHA_TEST_ENABLE */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 1); /* 0000000f UNK16A0 */ + xf_emit(ctx, 1, 0); /* 7/f MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_BACK_MASK */ + xf_emit(ctx, 3, 0); /* 00000007 STENCIL_BACK_OP_FAIL, ZFAIL, ZPASS */ + xf_emit(ctx, 4, 0); /* ffffffff BLEND_COLOR */ + xf_emit(ctx, 1, 0); /* 00000001 UNK19C0 */ + xf_emit(ctx, 1, 0); /* 00000001 UNK0FDC */ + xf_emit(ctx, 1, 0xf); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 7, 0); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 LOGIC_OP_ENABLE */ + xf_emit(ctx, 1, 0); /* ff[NV50]/3ff[NV84+] */ + xf_emit(ctx, 1, 4); /* 00000007 FP_CONTROL */ + xf_emit(ctx, 4, 0xffff); /* 0000ffff MSAA_MASK */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_MASK */ + xf_emit(ctx, 3, 0); /* 00000007 STENCIL_FRONT_OP_FAIL, ZFAIL, ZPASS */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_BACK_ENABLE */ + xf_emit(ctx, 2, 0); /* 00007fff WINDOW_OFFSET_XY */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK19CC */ + xf_emit(ctx, 1, 0); /* 7 */ + xf_emit(ctx, 1, 0); /* 00000001 SAMPLECNT_ENABLE */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + xf_emit(ctx, 1, 0); /* ffffffff COLOR_KEY */ + xf_emit(ctx, 1, 0); /* 00000001 COLOR_KEY_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000007 COLOR_KEY_FORMAT */ + xf_emit(ctx, 2, 0); /* ffffffff SIFC_BITMAP_COLOR */ + xf_emit(ctx, 1, 1); /* 00000001 SIFC_BITMAP_WRITE_BIT0_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000007 ALPHA_TEST_FUNC */ + xf_emit(ctx, 1, 0); /* 00000001 ALPHA_TEST_ENABLE */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 1, 3); /* 00000003 tesla UNK16B4 */ + xf_emit(ctx, 1, 0); /* 00000003 */ + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK1298 */ + } else if (dev_priv->chipset >= 0xa0) { + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK16B4 */ + xf_emit(ctx, 1, 0); /* 00000003 */ + } else { + xf_emit(ctx, 1, 0); /* 00000003 MULTISAMPLE_CTRL */ + } + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 8, 0); /* 00000001 BLEND_ENABLE */ + xf_emit(ctx, 1, 1); /* 0000001f BLEND_FUNC_DST_ALPHA */ + xf_emit(ctx, 1, 1); /* 00000007 BLEND_EQUATION_ALPHA */ + xf_emit(ctx, 1, 2); /* 0000001f BLEND_FUNC_SRC_ALPHA */ + xf_emit(ctx, 1, 1); /* 0000001f BLEND_FUNC_DST_RGB */ + xf_emit(ctx, 1, 1); /* 00000007 BLEND_EQUATION_RGB */ + xf_emit(ctx, 1, 2); /* 0000001f BLEND_FUNC_SRC_RGB */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 1, 0); /* 00000001 UNK12E4 */ + xf_emit(ctx, 8, 1); /* 00000007 IBLEND_EQUATION_RGB */ + xf_emit(ctx, 8, 1); /* 00000007 IBLEND_EQUATION_ALPHA */ + xf_emit(ctx, 8, 1); /* 00000001 IBLEND_UNK00 */ + xf_emit(ctx, 8, 2); /* 0000001f IBLEND_SRC_RGB */ + xf_emit(ctx, 8, 1); /* 0000001f IBLEND_DST_RGB */ + xf_emit(ctx, 8, 2); /* 0000001f IBLEND_SRC_ALPHA */ + xf_emit(ctx, 8, 1); /* 0000001f IBLEND_DST_ALPHA */ + xf_emit(ctx, 1, 0); /* 00000001 UNK1140 */ + } + xf_emit(ctx, 1, 1); /* 00000001 UNK133C */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 1, 0x11); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 7, 0); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 1, 0x0fac6881); /* 0fffffff RT_CONTROL */ + xf_emit(ctx, 1, 0); /* 00000001 LOGIC_OP_ENABLE */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + xf_emit(ctx, 1, 4); /* 00000007 FP_CONTROL */ + xf_emit(ctx, 1, 0); /* 00000003 UNK0F90 */ + xf_emit(ctx, 1, 0); /* 00000001 FRAMEBUFFER_SRGB */ + xf_emit(ctx, 1, 0); /* 7 */ + xf_emit(ctx, 1, 0x11); /* 3f/7f DST_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 DST_LINEAR */ + xf_emit(ctx, 1, 0); /* 00000007 OPERATION */ + xf_emit(ctx, 1, 0xcf); /* 000000ff SIFC_FORMAT */ + xf_emit(ctx, 1, 0xcf); /* 000000ff DRAW_COLOR_FORMAT */ + xf_emit(ctx, 1, 0xcf); /* 000000ff SRC_FORMAT */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ + xf_emit(ctx, 1, 0); /* 7/f[NVA3] MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 8, 0); /* 00000001 BLEND_ENABLE */ + xf_emit(ctx, 1, 1); /* 0000001f BLEND_FUNC_DST_ALPHA */ + xf_emit(ctx, 1, 1); /* 00000007 BLEND_EQUATION_ALPHA */ + xf_emit(ctx, 1, 2); /* 0000001f BLEND_FUNC_SRC_ALPHA */ + xf_emit(ctx, 1, 1); /* 0000001f BLEND_FUNC_DST_RGB */ + xf_emit(ctx, 1, 1); /* 00000007 BLEND_EQUATION_RGB */ + xf_emit(ctx, 1, 2); /* 0000001f BLEND_FUNC_SRC_RGB */ + xf_emit(ctx, 1, 1); /* 00000001 UNK133C */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 8, 1); /* 00000001 UNK19E0 */ + xf_emit(ctx, 1, 0x11); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 7, 0); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 1, 0x0fac6881); /* 0fffffff RT_CONTROL */ + xf_emit(ctx, 1, 0xf); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 7, 0); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 1, magic2); /* 001fffff tesla UNK0F78 */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_BOUNDS_EN */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0x11); /* 3f/7f DST_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 DST_LINEAR */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + if(dev_priv->chipset == 0x50) + xf_emit(ctx, 1, 0); /* ff */ + else + xf_emit(ctx, 3, 0); /* 1, 7, 3ff */ + xf_emit(ctx, 1, 4); /* 00000007 FP_CONTROL */ + xf_emit(ctx, 1, 0); /* 00000003 UNK0F90 */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000007 */ + xf_emit(ctx, 1, 0); /* 00000001 SAMPLECNT_ENABLE */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ + xf_emit(ctx, 1, 0); /* 7/f MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 1, 0x11); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 7, 0); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 1, 0x0fac6881); /* 0fffffff RT_CONTROL */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_BOUNDS_EN */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE_ENABLE */ + xf_emit(ctx, 1, 0x11); /* 3f/7f DST_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 DST_LINEAR */ + xf_emit(ctx, 1, 0); /* 000fffff BLIT_DU_DX_FRACT */ + xf_emit(ctx, 1, 1); /* 0001ffff BLIT_DU_DX_INT */ + xf_emit(ctx, 1, 0); /* 000fffff BLIT_DV_DY_FRACT */ + xf_emit(ctx, 1, 1); /* 0001ffff BLIT_DV_DY_INT */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + xf_emit(ctx, 1, magic1); /* 3ff/7ff tesla UNK0D68 */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK15B4 */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000007 */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + xf_emit(ctx, 8, 0); /* 0000ffff DMA_COLOR */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_GLOBAL */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_LOCAL */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_STACK */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_DST */ + xf_emit(ctx, 1, 0); /* 7 */ + xf_emit(ctx, 1, 0); /* 7/f MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 8, 0); /* 000000ff RT_ADDRESS_HIGH */ + xf_emit(ctx, 8, 0); /* ffffffff RT_LAYER_STRIDE */ + xf_emit(ctx, 8, 0); /* ffffffff RT_ADDRESS_LOW */ + xf_emit(ctx, 8, 8); /* 0000007f RT_TILE_MODE */ + xf_emit(ctx, 1, 0x11); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 7, 0); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 1, 0x0fac6881); /* 0fffffff RT_CONTROL */ + xf_emit(ctx, 8, 0x400); /* 0fffffff RT_HORIZ */ + xf_emit(ctx, 8, 0x300); /* 0000ffff RT_VERT */ + xf_emit(ctx, 1, 1); /* 00001fff RT_ARRAY_MODE */ + xf_emit(ctx, 1, 0xf); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 7, 0); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 1, 0x20); /* 00000fff DST_TILE_MODE */ + xf_emit(ctx, 1, 0x11); /* 3f/7f DST_FORMAT */ + xf_emit(ctx, 1, 0x100); /* 0001ffff DST_HEIGHT */ + xf_emit(ctx, 1, 0); /* 000007ff DST_LAYER */ + xf_emit(ctx, 1, 1); /* 00000001 DST_LINEAR */ + xf_emit(ctx, 1, 0); /* ffffffff DST_ADDRESS_LOW */ + xf_emit(ctx, 1, 0); /* 000000ff DST_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0x40); /* 0007ffff DST_PITCH */ + xf_emit(ctx, 1, 0x100); /* 0001ffff DST_WIDTH */ + xf_emit(ctx, 1, 0); /* 0000ffff */ + xf_emit(ctx, 1, 3); /* 00000003 tesla UNK15AC */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + xf_emit(ctx, 1, 0); /* 0001ffff GP_BUILTIN_RESULT_EN */ + xf_emit(ctx, 1, 0); /* 00000003 UNK0F90 */ + xf_emit(ctx, 1, 0); /* 00000007 */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + xf_emit(ctx, 1, magic2); /* 001fffff tesla UNK0F78 */ + xf_emit(ctx, 1, 0); /* 7/f MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 1, 2); /* 00000003 tesla UNK143C */ + xf_emit(ctx, 1, 0x0fac6881); /* 0fffffff RT_CONTROL */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_ZETA */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_BOUNDS_EN */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE_ENABLE */ + xf_emit(ctx, 2, 0); /* ffff, ff/3ff */ + xf_emit(ctx, 1, 0); /* 0001ffff GP_BUILTIN_RESULT_EN */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + xf_emit(ctx, 1, 0); /* 000000ff STENCIL_FRONT_MASK */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK15B4 */ + xf_emit(ctx, 1, 0); /* 00000007 */ + xf_emit(ctx, 1, 0); /* ffffffff ZETA_LAYER_STRIDE */ + xf_emit(ctx, 1, 0); /* 000000ff ZETA_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff ZETA_ADDRESS_LOW */ + xf_emit(ctx, 1, 4); /* 00000007 ZETA_TILE_MODE */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + xf_emit(ctx, 1, 0x400); /* 0fffffff ZETA_HORIZ */ + xf_emit(ctx, 1, 0x300); /* 0000ffff ZETA_VERT */ + xf_emit(ctx, 1, 0x1001); /* 00001fff ZETA_ARRAY_MODE */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ + xf_emit(ctx, 1, 0); /* 7/f MULTISAMPLE_SAMPLES_LOG2 */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 0); /* 00000001 */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 1, 0x11); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 7, 0); /* 3f/7f RT_FORMAT */ + xf_emit(ctx, 1, 0x0fac6881); /* 0fffffff RT_CONTROL */ + xf_emit(ctx, 1, 0xf); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 7, 0); /* 0000000f COLOR_MASK */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + xf_emit(ctx, 8, 0); /* 00000001 BLEND_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000003 UNK0F90 */ + xf_emit(ctx, 1, 0); /* 00000001 FRAMEBUFFER_SRGB */ + xf_emit(ctx, 1, 0); /* 7 */ + xf_emit(ctx, 1, 0); /* 00000001 LOGIC_OP_ENABLE */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 1, 0); /* 00000001 UNK1140 */ + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + } + xf_emit(ctx, 1, 0); /* 7/f MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000001 UNK1534 */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 1, 0x0fac6881); /* fffffff */ + xf_emit(ctx, 1, magic2); /* 001fffff tesla UNK0F78 */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_BOUNDS_EN */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE_ENABLE */ + xf_emit(ctx, 1, 0x11); /* 3f/7f DST_FORMAT */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK0FB0 */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + xf_emit(ctx, 1, 4); /* 00000007 FP_CONTROL */ + xf_emit(ctx, 1, 0); /* 00000001 STENCIL_FRONT_ENABLE */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK15B4 */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK19CC */ + xf_emit(ctx, 1, 0); /* 00000007 */ + xf_emit(ctx, 1, 0); /* 00000001 SAMPLECNT_ENABLE */ + xf_emit(ctx, 1, 0); /* 0000000f ZETA_FORMAT */ + xf_emit(ctx, 1, 1); /* 00000001 ZETA_ENABLE */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + xf_emit(ctx, 1, 0); /* 0000000f tesla UNK15C8 */ + } + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A3C */ + if (dev_priv->chipset >= 0xa0) { + xf_emit(ctx, 3, 0); /* 7/f, 1, ffff0ff3 */ + xf_emit(ctx, 1, 0xfac6881); /* fffffff */ + xf_emit(ctx, 4, 0); /* 1, 1, 1, 3ff */ + xf_emit(ctx, 1, 4); /* 7 */ + xf_emit(ctx, 1, 0); /* 1 */ + xf_emit(ctx, 2, 1); /* 1 */ + xf_emit(ctx, 2, 0); /* 7, f */ + xf_emit(ctx, 1, 1); /* 1 */ + xf_emit(ctx, 1, 0); /* 7/f */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 0x9, 0); /* 1 */ + else + xf_emit(ctx, 0x8, 0); /* 1 */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 8, 1); /* 1 */ + xf_emit(ctx, 1, 0x11); /* 7f */ + xf_emit(ctx, 7, 0); /* 7f */ + xf_emit(ctx, 1, 0xfac6881); /* fffffff */ + xf_emit(ctx, 1, 0xf); /* f */ + xf_emit(ctx, 7, 0); /* f */ + xf_emit(ctx, 1, 0x11); /* 7f */ + xf_emit(ctx, 1, 1); /* 1 */ + xf_emit(ctx, 5, 0); /* 1, 7, 3ff, 3, 7 */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 1, 0); /* 00000001 UNK1140 */ + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + } + } +} + +static void +nv50_graph_construct_xfer_tex(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + xf_emit(ctx, 2, 0); /* 1 LINKED_TSC. yes, 2. */ + if (dev_priv->chipset != 0x50) + xf_emit(ctx, 1, 0); /* 3 */ + xf_emit(ctx, 1, 1); /* 1ffff BLIT_DU_DX_INT */ + xf_emit(ctx, 1, 0); /* fffff BLIT_DU_DX_FRACT */ + xf_emit(ctx, 1, 1); /* 1ffff BLIT_DV_DY_INT */ + xf_emit(ctx, 1, 0); /* fffff BLIT_DV_DY_FRACT */ + if (dev_priv->chipset == 0x50) + xf_emit(ctx, 1, 0); /* 3 BLIT_CONTROL */ + else + xf_emit(ctx, 2, 0); /* 3ff, 1 */ + xf_emit(ctx, 1, 0x2a712488); /* ffffffff SRC_TIC_0 */ + xf_emit(ctx, 1, 0); /* ffffffff SRC_TIC_1 */ + xf_emit(ctx, 1, 0x4085c000); /* ffffffff SRC_TIC_2 */ + xf_emit(ctx, 1, 0x40); /* ffffffff SRC_TIC_3 */ + xf_emit(ctx, 1, 0x100); /* ffffffff SRC_TIC_4 */ + xf_emit(ctx, 1, 0x10100); /* ffffffff SRC_TIC_5 */ + xf_emit(ctx, 1, 0x02800000); /* ffffffff SRC_TIC_6 */ + xf_emit(ctx, 1, 0); /* ffffffff SRC_TIC_7 */ + if (dev_priv->chipset == 0x50) { + xf_emit(ctx, 1, 0); /* 00000001 turing UNK358 */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A34? */ + xf_emit(ctx, 1, 0); /* 00000003 turing UNK37C tesla UNK1690 */ + xf_emit(ctx, 1, 0); /* 00000003 BLIT_CONTROL */ + xf_emit(ctx, 1, 0); /* 00000001 turing UNK32C tesla UNK0F94 */ + } else if (!IS_NVAAF(dev_priv->chipset)) { + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A34? */ + xf_emit(ctx, 1, 0); /* 00000003 */ + xf_emit(ctx, 1, 0); /* 000003ff */ + xf_emit(ctx, 1, 0); /* 00000003 */ + xf_emit(ctx, 1, 0); /* 000003ff */ + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK1664 / turing UNK03E8 */ + xf_emit(ctx, 1, 0); /* 00000003 */ + xf_emit(ctx, 1, 0); /* 000003ff */ + } else { + xf_emit(ctx, 0x6, 0); + } + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A34 */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_TEXTURE */ + xf_emit(ctx, 1, 0); /* 0000ffff DMA_SRC */ +} + +static void +nv50_graph_construct_xfer_unk8cxx(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + xf_emit(ctx, 1, 0); /* 00000001 UNK1534 */ + xf_emit(ctx, 1, 0); /* 7/f MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 2, 0); /* 7, ffff0ff3 */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE */ + xf_emit(ctx, 1, 0x04e3bfdf); /* ffffffff UNK0D64 */ + xf_emit(ctx, 1, 0x04e3bfdf); /* ffffffff UNK0DF4 */ + xf_emit(ctx, 1, 1); /* 00000001 UNK15B4 */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_STIPPLE_ENABLE */ + xf_emit(ctx, 1, 0x00ffff00); /* 00ffffff LINE_STIPPLE_PATTERN */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK0F98 */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK1668 */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_STIPPLE_ENABLE */ + xf_emit(ctx, 1, 0x00ffff00); /* 00ffffff LINE_STIPPLE_PATTERN */ + xf_emit(ctx, 1, 0); /* 00000001 POLYGON_SMOOTH_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 UNK1534 */ + xf_emit(ctx, 1, 0); /* 7/f MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1658 */ + xf_emit(ctx, 1, 0); /* 00000001 LINE_SMOOTH_ENABLE */ + xf_emit(ctx, 1, 0); /* ffff0ff3 */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 DEPTH_WRITE */ + xf_emit(ctx, 1, 1); /* 00000001 UNK15B4 */ + xf_emit(ctx, 1, 0); /* 00000001 POINT_SPRITE_ENABLE */ + xf_emit(ctx, 1, 1); /* 00000001 tesla UNK165C */ + xf_emit(ctx, 1, 0x30201000); /* ffffffff tesla UNK1670 */ + xf_emit(ctx, 1, 0x70605040); /* ffffffff tesla UNK1670 */ + xf_emit(ctx, 1, 0xb8a89888); /* ffffffff tesla UNK1670 */ + xf_emit(ctx, 1, 0xf8e8d8c8); /* ffffffff tesla UNK1670 */ + xf_emit(ctx, 1, 0); /* 00000001 VERTEX_TWO_SIDE_ENABLE */ + xf_emit(ctx, 1, 0x1a); /* 0000001f POLYGON_MODE */ +} + +static void +nv50_graph_construct_xfer_tp(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + if (dev_priv->chipset < 0xa0) { + nv50_graph_construct_xfer_unk84xx(ctx); + nv50_graph_construct_xfer_tprop(ctx); + nv50_graph_construct_xfer_tex(ctx); + nv50_graph_construct_xfer_unk8cxx(ctx); + } else { + nv50_graph_construct_xfer_tex(ctx); + nv50_graph_construct_xfer_tprop(ctx); + nv50_graph_construct_xfer_unk8cxx(ctx); + nv50_graph_construct_xfer_unk84xx(ctx); + } +} + +static void +nv50_graph_construct_xfer_mpc(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int i, mpcnt = 2; + switch (dev_priv->chipset) { + case 0x98: + case 0xaa: + mpcnt = 1; + break; + case 0x50: + case 0x84: + case 0x86: + case 0x92: + case 0x94: + case 0x96: + case 0xa8: + case 0xac: + mpcnt = 2; + break; + case 0xa0: + case 0xa3: + case 0xa5: + case 0xaf: + mpcnt = 3; + break; + } + for (i = 0; i < mpcnt; i++) { + xf_emit(ctx, 1, 0); /* ff */ + xf_emit(ctx, 1, 0x80); /* ffffffff tesla UNK1404 */ + xf_emit(ctx, 1, 0x80007004); /* ffffffff tesla UNK12B0 */ + xf_emit(ctx, 1, 0x04000400); /* ffffffff */ + if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 1, 0xc0); /* 00007fff tesla UNK152C */ + xf_emit(ctx, 1, 0x1000); /* 0000ffff tesla UNK0D60 */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A30 */ + if (dev_priv->chipset == 0x86 || dev_priv->chipset == 0x98 || dev_priv->chipset == 0xa8 || IS_NVAAF(dev_priv->chipset)) { + xf_emit(ctx, 1, 0xe00); /* 7fff */ + xf_emit(ctx, 1, 0x1e00); /* 7fff */ + } + xf_emit(ctx, 1, 1); /* 000000ff VP_REG_ALLOC_TEMP */ + xf_emit(ctx, 1, 0); /* 00000001 LINKED_TSC */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + if (dev_priv->chipset == 0x50) + xf_emit(ctx, 2, 0x1000); /* 7fff tesla UNK141C */ + xf_emit(ctx, 1, 1); /* 000000ff GP_REG_ALLOC_TEMP */ + xf_emit(ctx, 1, 0); /* 00000001 GP_ENABLE */ + xf_emit(ctx, 1, 4); /* 000000ff FP_REG_ALLOC_TEMP */ + xf_emit(ctx, 1, 2); /* 00000003 REG_MODE */ + if (IS_NVAAF(dev_priv->chipset)) + xf_emit(ctx, 0xb, 0); /* RO */ + else if (dev_priv->chipset >= 0xa0) + xf_emit(ctx, 0xc, 0); /* RO */ + else + xf_emit(ctx, 0xa, 0); /* RO */ + } + xf_emit(ctx, 1, 0x08100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + if (dev_priv->chipset >= 0xa0) { + xf_emit(ctx, 1, 0x1fe21); /* 0003ffff tesla UNK0FAC */ + } + xf_emit(ctx, 3, 0); /* 7fff, 0, 0 */ + xf_emit(ctx, 1, 0); /* 00000001 tesla UNK1534 */ + xf_emit(ctx, 1, 0); /* 7/f MULTISAMPLE_SAMPLES_LOG2 */ + xf_emit(ctx, 4, 0xffff); /* 0000ffff MSAA_MASK */ + xf_emit(ctx, 1, 1); /* 00000001 LANES32 */ + xf_emit(ctx, 1, 0x10001); /* 00ffffff BLOCK_ALLOC */ + xf_emit(ctx, 1, 0x10001); /* ffffffff BLOCKDIM_XY */ + xf_emit(ctx, 1, 1); /* 0000ffff BLOCKDIM_Z */ + xf_emit(ctx, 1, 0); /* ffffffff SHARED_SIZE */ + xf_emit(ctx, 1, 0x1fe21); /* 1ffff/3ffff[NVA0+] tesla UNk0FAC */ + xf_emit(ctx, 1, 0); /* ffffffff tesla UNK1A34 */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 1); /* 0000001f tesla UNK169C */ + xf_emit(ctx, 1, 0); /* ff/3ff */ + xf_emit(ctx, 1, 0); /* 1 LINKED_TSC */ + xf_emit(ctx, 1, 0); /* ff FP_ADDRESS_HIGH */ + xf_emit(ctx, 1, 0); /* ffffffff FP_ADDRESS_LOW */ + xf_emit(ctx, 1, 0x08100c12); /* 1fffffff FP_INTERPOLANT_CTRL */ + xf_emit(ctx, 1, 4); /* 00000007 FP_CONTROL */ + xf_emit(ctx, 1, 0); /* 000000ff FRAG_COLOR_CLAMP_EN */ + xf_emit(ctx, 1, 2); /* 00000003 REG_MODE */ + xf_emit(ctx, 1, 0x11); /* 0000007f RT_FORMAT */ + xf_emit(ctx, 7, 0); /* 0000007f RT_FORMAT */ + xf_emit(ctx, 1, 0); /* 00000007 */ + xf_emit(ctx, 1, 0xfac6881); /* 0fffffff RT_CONTROL */ + xf_emit(ctx, 1, 0); /* 00000003 MULTISAMPLE_CTRL */ + if (IS_NVA3F(dev_priv->chipset)) + xf_emit(ctx, 1, 3); /* 00000003 tesla UNK16B4 */ + xf_emit(ctx, 1, 0); /* 00000001 ALPHA_TEST_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000007 ALPHA_TEST_FUNC */ + xf_emit(ctx, 1, 0); /* 00000001 FRAMEBUFFER_SRGB */ + xf_emit(ctx, 1, 4); /* ffffffff tesla UNK1400 */ + xf_emit(ctx, 8, 0); /* 00000001 BLEND_ENABLE */ + xf_emit(ctx, 1, 0); /* 00000001 LOGIC_OP_ENABLE */ + xf_emit(ctx, 1, 2); /* 0000001f BLEND_FUNC_SRC_RGB */ + xf_emit(ctx, 1, 1); /* 0000001f BLEND_FUNC_DST_RGB */ + xf_emit(ctx, 1, 1); /* 00000007 BLEND_EQUATION_RGB */ + xf_emit(ctx, 1, 2); /* 0000001f BLEND_FUNC_SRC_ALPHA */ + xf_emit(ctx, 1, 1); /* 0000001f BLEND_FUNC_DST_ALPHA */ + xf_emit(ctx, 1, 1); /* 00000007 BLEND_EQUATION_ALPHA */ + xf_emit(ctx, 1, 1); /* 00000001 UNK133C */ + if (IS_NVA3F(dev_priv->chipset)) { + xf_emit(ctx, 1, 0); /* 00000001 UNK12E4 */ + xf_emit(ctx, 8, 2); /* 0000001f IBLEND_FUNC_SRC_RGB */ + xf_emit(ctx, 8, 1); /* 0000001f IBLEND_FUNC_DST_RGB */ + xf_emit(ctx, 8, 1); /* 00000007 IBLEND_EQUATION_RGB */ + xf_emit(ctx, 8, 2); /* 0000001f IBLEND_FUNC_SRC_ALPHA */ + xf_emit(ctx, 8, 1); /* 0000001f IBLEND_FUNC_DST_ALPHA */ + xf_emit(ctx, 8, 1); /* 00000007 IBLEND_EQUATION_ALPHA */ + xf_emit(ctx, 8, 1); /* 00000001 IBLEND_UNK00 */ + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK1928 */ + xf_emit(ctx, 1, 0); /* 00000001 UNK1140 */ + } + xf_emit(ctx, 1, 0); /* 00000003 tesla UNK0F90 */ + xf_emit(ctx, 1, 4); /* 000000ff FP_RESULT_COUNT */ + /* XXX: demagic this part some day */ + if (dev_priv->chipset == 0x50) + xf_emit(ctx, 0x3a0, 0); + else if (dev_priv->chipset < 0x94) + xf_emit(ctx, 0x3a2, 0); + else if (dev_priv->chipset == 0x98 || dev_priv->chipset == 0xaa) + xf_emit(ctx, 0x39f, 0); + else + xf_emit(ctx, 0x3a3, 0); + xf_emit(ctx, 1, 0x11); /* 3f/7f DST_FORMAT */ + xf_emit(ctx, 1, 0); /* 7 OPERATION */ + xf_emit(ctx, 1, 1); /* 1 DST_LINEAR */ + xf_emit(ctx, 0x2d, 0); +} + +static void +nv50_graph_construct_xfer2(struct nouveau_grctx *ctx) +{ + struct drm_nouveau_private *dev_priv = ctx->dev->dev_private; + int i; + uint32_t offset; + uint32_t units = nv_rd32 (ctx->dev, 0x1540); + int size = 0; + + offset = (ctx->ctxvals_pos+0x3f)&~0x3f; + + if (dev_priv->chipset < 0xa0) { + for (i = 0; i < 8; i++) { + ctx->ctxvals_pos = offset + i; + /* that little bugger belongs to csched. No idea + * what it's doing here. */ + if (i == 0) + xf_emit(ctx, 1, 0x08100c12); /* FP_INTERPOLANT_CTRL */ + if (units & (1 << i)) + nv50_graph_construct_xfer_mpc(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + } + } else { + /* Strand 0: TPs 0, 1 */ + ctx->ctxvals_pos = offset; + /* that little bugger belongs to csched. No idea + * what it's doing here. */ + xf_emit(ctx, 1, 0x08100c12); /* FP_INTERPOLANT_CTRL */ + if (units & (1 << 0)) + nv50_graph_construct_xfer_mpc(ctx); + if (units & (1 << 1)) + nv50_graph_construct_xfer_mpc(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 1: TPs 2, 3 */ + ctx->ctxvals_pos = offset + 1; + if (units & (1 << 2)) + nv50_graph_construct_xfer_mpc(ctx); + if (units & (1 << 3)) + nv50_graph_construct_xfer_mpc(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 2: TPs 4, 5, 6 */ + ctx->ctxvals_pos = offset + 2; + if (units & (1 << 4)) + nv50_graph_construct_xfer_mpc(ctx); + if (units & (1 << 5)) + nv50_graph_construct_xfer_mpc(ctx); + if (units & (1 << 6)) + nv50_graph_construct_xfer_mpc(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + + /* Strand 3: TPs 7, 8, 9 */ + ctx->ctxvals_pos = offset + 3; + if (units & (1 << 7)) + nv50_graph_construct_xfer_mpc(ctx); + if (units & (1 << 8)) + nv50_graph_construct_xfer_mpc(ctx); + if (units & (1 << 9)) + nv50_graph_construct_xfer_mpc(ctx); + if ((ctx->ctxvals_pos-offset)/8 > size) + size = (ctx->ctxvals_pos-offset)/8; + } + ctx->ctxvals_pos = offset + size * 8; + ctx->ctxvals_pos = (ctx->ctxvals_pos+0x3f)&~0x3f; + cp_lsr (ctx, offset); + cp_out (ctx, CP_SET_XFER_POINTER); + cp_lsr (ctx, size); + cp_out (ctx, CP_SEEK_2); + cp_out (ctx, CP_XFER_2); + cp_wait(ctx, XFER, BUSY); +} diff --git a/driver/pscnv/nv50_pm.c b/driver/pscnv/nv50_pm.c new file mode 100644 index 00000000..adc2ec78 --- /dev/null +++ b/driver/pscnv/nv50_pm.c @@ -0,0 +1,134 @@ +/* + * Copyright 2010 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_bios.h" +#include "nouveau_pm.h" + +struct nv50_pm_state { + struct nouveau_pm_level *perflvl; + struct pll_lims pll; + enum pll_types type; + int N, M, P; +}; + +int +nv50_pm_clock_get(struct drm_device *dev, u32 id) +{ + struct pll_lims pll; + int P, N, M, ret; + u32 reg0, reg1; + + ret = get_pll_limits(dev, id, &pll); + if (ret) + return ret; + + reg0 = nv_rd32(dev, pll.reg + 0); + reg1 = nv_rd32(dev, pll.reg + 4); + P = (reg0 & 0x00070000) >> 16; + N = (reg1 & 0x0000ff00) >> 8; + M = (reg1 & 0x000000ff); + + if (M > 0) + return ((pll.refclk * N / M) >> P); + else + return -EINVAL; +} + +void * +nv50_pm_clock_pre(struct drm_device *dev, struct nouveau_pm_level *perflvl, + u32 id, int khz) +{ + struct nv50_pm_state *state; + int dummy, ret; + + state = kzalloc(sizeof(*state), GFP_KERNEL); + if (!state) + return ERR_PTR(-ENOMEM); + state->type = id; + state->perflvl = perflvl; + + ret = get_pll_limits(dev, id, &state->pll); + if (ret < 0) { + kfree(state); + return (ret == -ENOENT) ? NULL : ERR_PTR(ret); + } + + ret = nv50_calc_pll(dev, &state->pll, khz, &state->N, &state->M, + &dummy, &dummy, &state->P); + if (ret < 0) { + kfree(state); + return ERR_PTR(ret); + } + + return state; +} + +void +nv50_pm_clock_set(struct drm_device *dev, void *pre_state) +{ + struct nv50_pm_state *state = pre_state; + struct nouveau_pm_level *perflvl = state->perflvl; + u32 reg = state->pll.reg, tmp; + struct bit_entry BIT_M; + u16 script; + int N = state->N; + int M = state->M; + int P = state->P; + + if (state->type == PLL_MEMORY && perflvl->memscript && + bit_table(dev, 'M', &BIT_M) == 0 && + BIT_M.version == 1 && BIT_M.length >= 0x0b) { + script = ROM16(BIT_M.data[0x05]); + if (script) + nouveau_bios_run_init_table(dev, script, NULL); + script = ROM16(BIT_M.data[0x07]); + if (script) + nouveau_bios_run_init_table(dev, script, NULL); + script = ROM16(BIT_M.data[0x09]); + if (script) + nouveau_bios_run_init_table(dev, script, NULL); + + nouveau_bios_run_init_table(dev, perflvl->memscript, NULL); + } + + if (state->type == PLL_MEMORY) { + nv_wr32(dev, 0x100210, 0); + nv_wr32(dev, 0x1002dc, 1); + } + + tmp = nv_rd32(dev, reg + 0) & 0xfff8ffff; + tmp |= 0x80000000 | (P << 16); + nv_wr32(dev, reg + 0, tmp); + nv_wr32(dev, reg + 4, (N << 8) | M); + + if (state->type == PLL_MEMORY) { + nv_wr32(dev, 0x1002dc, 0); + nv_wr32(dev, 0x100210, 0x80000000); + } + + kfree(state); +} + diff --git a/driver/pscnv/nv50_sor.c b/driver/pscnv/nv50_sor.c new file mode 100644 index 00000000..b4a5ecb1 --- /dev/null +++ b/driver/pscnv/nv50_sor.c @@ -0,0 +1,343 @@ +/* + * Copyright (C) 2008 Maarten Maathuis. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include "drmP.h" +#include "drm_crtc_helper.h" + +#define NOUVEAU_DMA_DEBUG (nouveau_reg_debug & NOUVEAU_REG_DEBUG_EVO) +#include "nouveau_reg.h" +#include "nouveau_drv.h" +#include "nouveau_dma.h" +#include "nouveau_encoder.h" +#include "nouveau_connector.h" +#include "nouveau_crtc.h" +#include "nv50_display.h" + +static void +nv50_sor_disconnect(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + int ret; + + if (!nv_encoder->crtc) + return; + nv50_crtc_blank(nouveau_crtc(nv_encoder->crtc), true); + + NV_DEBUG_KMS(dev, "Disconnecting SOR %d\n", nv_encoder->or); + + ret = RING_SPACE(evo, 4); + if (ret) { + NV_ERROR(dev, "no space while disconnecting SOR\n"); + return; + } + BEGIN_RING(evo, 0, NV50_EVO_SOR(nv_encoder->or, MODE_CTRL), 1); + OUT_RING (evo, 0); + BEGIN_RING(evo, 0, NV50_EVO_UPDATE, 1); + OUT_RING (evo, 0); + + nv_encoder->crtc = NULL; + nv_encoder->last_dpms = DRM_MODE_DPMS_OFF; +} + +static void +nv50_sor_dpms(struct drm_encoder *encoder, int mode) +{ + struct drm_device *dev = encoder->dev; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_encoder *enc; + uint32_t val; + int or = nv_encoder->or; + + NV_DEBUG_KMS(dev, "or %d type %d mode %d\n", or, nv_encoder->dcb->type, mode); + + nv_encoder->last_dpms = mode; + list_for_each_entry(enc, &dev->mode_config.encoder_list, head) { + struct nouveau_encoder *nvenc = nouveau_encoder(enc); + + if (nvenc == nv_encoder || + (nvenc->dcb->type != OUTPUT_TMDS && + nvenc->dcb->type != OUTPUT_LVDS && + nvenc->dcb->type != OUTPUT_DP) || + nvenc->dcb->or != nv_encoder->dcb->or) + continue; + + if (nvenc->last_dpms == DRM_MODE_DPMS_ON) + return; + } + + /* wait for it to be done */ + if (!nv_wait(dev, NV50_PDISPLAY_SOR_DPMS_CTRL(or), + NV50_PDISPLAY_SOR_DPMS_CTRL_PENDING, 0)) { + NV_ERROR(dev, "timeout: SOR_DPMS_CTRL_PENDING(%d) == 0\n", or); + NV_ERROR(dev, "SOR_DPMS_CTRL(%d) = 0x%08x\n", or, + nv_rd32(dev, NV50_PDISPLAY_SOR_DPMS_CTRL(or))); + } + + val = nv_rd32(dev, NV50_PDISPLAY_SOR_DPMS_CTRL(or)); + + if (mode == DRM_MODE_DPMS_ON) + val |= NV50_PDISPLAY_SOR_DPMS_CTRL_ON; + else + val &= ~NV50_PDISPLAY_SOR_DPMS_CTRL_ON; + + nv_wr32(dev, NV50_PDISPLAY_SOR_DPMS_CTRL(or), val | + NV50_PDISPLAY_SOR_DPMS_CTRL_PENDING); + if (!nv_wait(dev, NV50_PDISPLAY_SOR_DPMS_STATE(or), + NV50_PDISPLAY_SOR_DPMS_STATE_WAIT, 0)) { + NV_ERROR(dev, "timeout: SOR_DPMS_STATE_WAIT(%d) == 0\n", or); + NV_ERROR(dev, "SOR_DPMS_STATE(%d) = 0x%08x\n", or, + nv_rd32(dev, NV50_PDISPLAY_SOR_DPMS_STATE(or))); + } + + if (nv_encoder->dcb->type == OUTPUT_DP) { + struct nouveau_i2c_chan *auxch; + + auxch = nouveau_i2c_find(dev, nv_encoder->dcb->i2c_index); + if (!auxch) + return; + + if (mode == DRM_MODE_DPMS_ON) { + u8 status = DP_SET_POWER_D0; + nouveau_dp_auxch(auxch, 8, DP_SET_POWER, &status, 1); + nouveau_dp_link_train(encoder); + } else { + u8 status = DP_SET_POWER_D3; + nouveau_dp_auxch(auxch, 8, DP_SET_POWER, &status, 1); + } + } +} + +static void +nv50_sor_save(struct drm_encoder *encoder) +{ + NV_ERROR(encoder->dev, "!!\n"); +} + +static void +nv50_sor_restore(struct drm_encoder *encoder) +{ + NV_ERROR(encoder->dev, "!!\n"); +} + +static bool +nv50_sor_mode_fixup(struct drm_encoder *encoder, struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct nouveau_connector *connector; + + NV_DEBUG_KMS(encoder->dev, "or %d\n", nv_encoder->or); + + connector = nouveau_encoder_connector_get(nv_encoder); + if (!connector) { + NV_ERROR(encoder->dev, "Encoder has no connector\n"); + return false; + } + + if (connector->scaling_mode != DRM_MODE_SCALE_NONE && + connector->native_mode) { + int id = adjusted_mode->base.id; + *adjusted_mode = *connector->native_mode; + adjusted_mode->base.id = id; + } + + return true; +} + +static void +nv50_sor_prepare(struct drm_encoder *encoder) +{ +} + +static void +nv50_sor_commit(struct drm_encoder *encoder) +{ +} + +static void +nv50_sor_mode_set(struct drm_encoder *encoder, struct drm_display_mode *mode, + struct drm_display_mode *adjusted_mode) +{ + struct drm_nouveau_private *dev_priv = encoder->dev->dev_private; + struct nouveau_channel *evo = dev_priv->evo; + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct nouveau_crtc *crtc = nouveau_crtc(encoder->crtc); + uint32_t mode_ctl = 0; + int ret; + + NV_DEBUG_KMS(dev, "or %d type %d -> crtc %d\n", + nv_encoder->or, nv_encoder->dcb->type, crtc->index); + + nv50_sor_dpms(encoder, DRM_MODE_DPMS_ON); + + switch (nv_encoder->dcb->type) { + case OUTPUT_TMDS: + if (nv_encoder->dcb->sorconf.link & 1) { + if (adjusted_mode->clock < 165000) + mode_ctl = 0x0100; + else + mode_ctl = 0x0500; + } else + mode_ctl = 0x0200; + break; + case OUTPUT_DP: + mode_ctl |= (nv_encoder->dp.mc_unknown << 16); + if (nv_encoder->dcb->sorconf.link & 1) + mode_ctl |= 0x00000800; + else + mode_ctl |= 0x00000900; + break; + default: + break; + } + + if (crtc->index == 1) + mode_ctl |= NV50_EVO_SOR_MODE_CTRL_CRTC1; + else + mode_ctl |= NV50_EVO_SOR_MODE_CTRL_CRTC0; + + if (adjusted_mode->flags & DRM_MODE_FLAG_NHSYNC) + mode_ctl |= NV50_EVO_SOR_MODE_CTRL_NHSYNC; + + if (adjusted_mode->flags & DRM_MODE_FLAG_NVSYNC) + mode_ctl |= NV50_EVO_SOR_MODE_CTRL_NVSYNC; + + ret = RING_SPACE(evo, 2); + if (ret) { + NV_ERROR(dev, "no space while connecting SOR\n"); + return; + } + BEGIN_RING(evo, 0, NV50_EVO_SOR(nv_encoder->or, MODE_CTRL), 1); + OUT_RING(evo, mode_ctl); + + nv_encoder->crtc = encoder->crtc; +} + +static struct drm_crtc * +nv50_sor_crtc_get(struct drm_encoder *encoder) +{ + return nouveau_encoder(encoder)->crtc; +} + +static const struct drm_encoder_helper_funcs nv50_sor_helper_funcs = { + .dpms = nv50_sor_dpms, + .save = nv50_sor_save, + .restore = nv50_sor_restore, + .mode_fixup = nv50_sor_mode_fixup, + .prepare = nv50_sor_prepare, + .commit = nv50_sor_commit, + .mode_set = nv50_sor_mode_set, + .get_crtc = nv50_sor_crtc_get, + .detect = NULL, + .disable = nv50_sor_disconnect +}; + +static void +nv50_sor_destroy(struct drm_encoder *encoder) +{ + struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder); + + if (!encoder) + return; + + NV_DEBUG_KMS(encoder->dev, "\n"); + + drm_encoder_cleanup(encoder); + + kfree(nv_encoder); +} + +static const struct drm_encoder_funcs nv50_sor_encoder_funcs = { + .destroy = nv50_sor_destroy, +}; + +int +nv50_sor_create(struct drm_connector *connector, struct dcb_entry *entry) +{ + struct nouveau_encoder *nv_encoder = NULL; + struct drm_device *dev = connector->dev; + struct drm_encoder *encoder; + int type; + + NV_DEBUG_KMS(dev, "\n"); + + switch (entry->type) { + case OUTPUT_TMDS: + case OUTPUT_DP: + type = DRM_MODE_ENCODER_TMDS; + break; + case OUTPUT_LVDS: + type = DRM_MODE_ENCODER_LVDS; + break; + default: + return -EINVAL; + } + + nv_encoder = kzalloc(sizeof(*nv_encoder), GFP_KERNEL); + if (!nv_encoder) + return -ENOMEM; + encoder = to_drm_encoder(nv_encoder); + + nv_encoder->dcb = entry; + nv_encoder->or = ffs(entry->or) - 1; + nv_encoder->last_dpms = DRM_MODE_DPMS_OFF; + + drm_encoder_init(dev, encoder, &nv50_sor_encoder_funcs, type); + drm_encoder_helper_add(encoder, &nv50_sor_helper_funcs); + + encoder->possible_crtcs = entry->heads; + encoder->possible_clones = 0; + + if (nv_encoder->dcb->type == OUTPUT_DP) { + int or = nv_encoder->or, link = !(entry->dpconf.sor.link & 1); + uint32_t tmp; + + tmp = nv_rd32(dev, 0x61c700 + (or * 0x800)); + + switch ((tmp & 0x00000f00) >> 8) { + case 8: + case 9: + nv_encoder->dp.mc_unknown = (tmp & 0x000f0000) >> 16; + tmp = nv_rd32(dev, NV50_SOR_DP_CTRL(or, link)); + nv_encoder->dp.unk0 = tmp & 0x000001fc; + tmp = nv_rd32(dev, NV50_SOR_DP_UNK128(or, link)); + nv_encoder->dp.unk1 = tmp & 0x010f7f3f; + break; + default: + break; + } + + if (!nv_encoder->dp.mc_unknown) + nv_encoder->dp.mc_unknown = 5; + } + + drm_mode_connector_attach_encoder(connector, encoder); + return 0; +} diff --git a/driver/pscnv/nv50_vm.c b/driver/pscnv/nv50_vm.c new file mode 100644 index 00000000..6242a8f1 --- /dev/null +++ b/driver/pscnv/nv50_vm.c @@ -0,0 +1,557 @@ +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "nv50_vm.h" +#include "pscnv_vm.h" +#include "nv50_chan.h" +#include "pscnv_chan.h" + +int nv50_vm_map_kernel(struct pscnv_bo *bo); +void nv50_vm_takedown(struct drm_device *dev); +int nv50_vspace_do_unmap (struct pscnv_vspace *vs, uint64_t offset, uint64_t length); + +int +nv50_vm_flush(struct drm_device *dev, int unit) { + nv_wr32(dev, 0x100c80, unit << 16 | 1); + if (!nouveau_wait_until(dev, 2000000000ULL, 0x100c80, 1, 0)) { + NV_ERROR(dev, "TLB flush fail on unit %d!\n", unit); + return -EIO; + } + return 0; +} + +int nv50_vspace_tlb_flush (struct pscnv_vspace *vs) { + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + int i, ret; + nv50_vm_flush(vs->dev, 5); /* PFIFO always active */ + for (i = 0; i < PSCNV_ENGINES_NUM; i++) { + struct pscnv_engine *eng = dev_priv->engines[i]; + if (nv50_vs(vs)->engref[i]) + if ((ret = eng->tlb_flush(eng, vs))) + return ret; + } + return 0; +} + +static int +nv50_vspace_fill_pd_slot (struct pscnv_vspace *vs, uint32_t pdenum) { + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + struct list_head *pos; + int i; + uint32_t chan_pd; + nv50_vs(vs)->pt[pdenum] = pscnv_mem_alloc(vs->dev, NV50_VM_SPTE_COUNT * 8, PSCNV_GEM_CONTIG, 0, 0xa9e7ab1e); + if (!nv50_vs(vs)->pt[pdenum]) { + return -ENOMEM; + } + + if (vs->vid != -1) + nv50_vm_map_kernel(nv50_vs(vs)->pt[pdenum]); + + for (i = 0; i < NV50_VM_SPTE_COUNT; i++) + nv_wv32(nv50_vs(vs)->pt[pdenum], i * 8, 0); + + if (dev_priv->chipset == 0x50) + chan_pd = NV50_CHAN_PD; + else + chan_pd = NV84_CHAN_PD; + + list_for_each(pos, &nv50_vs(vs)->chan_list) { + struct pscnv_chan *ch = list_entry(pos, struct pscnv_chan, vspace_list); + uint64_t pde = nv50_vs(vs)->pt[pdenum]->start | 3; + nv_wv32(ch->bo, chan_pd + pdenum * 8 + 4, pde >> 32); + nv_wv32(ch->bo, chan_pd + pdenum * 8, pde); + } + return 0; +} + +int +nv50_vspace_place_map (struct pscnv_vspace *vs, struct pscnv_bo *bo, + uint64_t start, uint64_t end, int back, + struct pscnv_mm_node **res) { + return pscnv_mm_alloc(vs->mm, bo->size, back?PSCNV_MM_FROMBACK:0, start, end, res); +} + +static int nv50_vspace_map_contig_range (struct pscnv_vspace *vs, uint64_t offset, uint64_t pte, uint64_t size, int lp) { + int ret; + /* XXX: add LP support */ + BUG_ON(lp); + while (size) { + uint32_t pgnum = offset / 0x1000; + uint32_t pdenum = pgnum / NV50_VM_SPTE_COUNT; + uint32_t ptenum = pgnum % NV50_VM_SPTE_COUNT; + int lev = 0; + int i; + while (lev < 7 && size >= (0x1000 << (lev + 1)) && !(offset & (1 << (lev + 12)))) + lev++; + if (!nv50_vs(vs)->pt[pdenum]) + if ((ret = nv50_vspace_fill_pd_slot (vs, pdenum))) + return ret; + for (i = 0; i < (1 << lev); i++) { + nv_wv32(nv50_vs(vs)->pt[pdenum], (ptenum + i) * 8 + 4, pte >> 32); + nv_wv32(nv50_vs(vs)->pt[pdenum], (ptenum + i) * 8, pte | lev << 7); + if (pscnv_vm_debug >= 3) + NV_INFO(vs->dev, "VM: [%08x][%08x] = %016llx\n", pdenum, ptenum + i, pte | lev << 7); + } + size -= (0x1000 << lev); + offset += (0x1000 << lev); + pte += (0x1000 << lev); + } + return 0; +} + +int +nv50_vspace_do_map (struct pscnv_vspace *vs, struct pscnv_bo *bo, uint64_t offset) { + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + struct pscnv_mm_node *n; + int ret, i; + uint64_t roff = 0; + switch (bo->flags & PSCNV_GEM_MEMTYPE_MASK) { + case PSCNV_GEM_VRAM_SMALL: + case PSCNV_GEM_VRAM_LARGE: + for (n = bo->mmnode; n; n = n->next) { + /* XXX: add LP support */ + uint64_t pte = n->start; + if (dev_priv->chipset == 0xaa || dev_priv->chipset == 0xac || dev_priv->chipset == 0xaf) { + pte += dev_priv->vram_sys_base; + pte |= 0x30; + } + pte |= (uint64_t)bo->tile_flags << 40; + pte |= 1; /* present */ + if ((ret = nv50_vspace_map_contig_range(vs, offset + roff, pte, n->size, 0))) { + nv50_vspace_do_unmap (vs, offset, bo->size); + return ret; + } + roff += n->size; + } + break; + case PSCNV_GEM_SYSRAM_SNOOP: + case PSCNV_GEM_SYSRAM_NOSNOOP: + for (i = 0; i < (bo->size >> PAGE_SHIFT); i++) { + uint64_t pte = bo->dmapages[i]; + pte |= (uint64_t)bo->tile_flags << 40; + pte |= 1; + if ((bo->flags & PSCNV_GEM_MEMTYPE_MASK) == PSCNV_GEM_SYSRAM_SNOOP) + pte |= 0x20; + else + pte |= 0x30; + if ((ret = nv50_vspace_map_contig_range(vs, offset + roff, pte, PAGE_SIZE, 0))) { + nv50_vspace_do_unmap (vs, offset, bo->size); + return ret; + } + roff += PAGE_SIZE; + } + break; + default: + return -ENOSYS; + } + dev_priv->vm->bar_flush(vs->dev); + return 0; +} + +int +nv50_vspace_do_unmap (struct pscnv_vspace *vs, uint64_t offset, uint64_t length) { + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + while (length) { + uint32_t pgnum = offset / 0x1000; + uint32_t pdenum = pgnum / NV50_VM_SPTE_COUNT; + uint32_t ptenum = pgnum % NV50_VM_SPTE_COUNT; + if (nv50_vs(vs)->pt[pdenum]) { + nv_wv32(nv50_vs(vs)->pt[pdenum], ptenum * 8, 0); + } + offset += 0x1000; + length -= 0x1000; + } + dev_priv->vm->bar_flush(vs->dev); + if (vs->vid == -1) { + return nv50_vm_flush(vs->dev, 6); + } else { + nv50_vspace_tlb_flush(vs); + } + return 0; +} + +int nv50_vspace_new(struct pscnv_vspace *vs) { + int ret; + + /* XXX: could actually use it some day... */ + if (vs->size > 1ull << 40) + return -EINVAL; + + vs->engdata = kzalloc(sizeof(struct nv50_vspace), GFP_KERNEL); + if (!vs->engdata) { + NV_ERROR(vs->dev, "VM: Couldn't alloc vspace eng\n"); + return -ENOMEM; + } + INIT_LIST_HEAD(&nv50_vs(vs)->chan_list); + ret = pscnv_mm_init(vs->dev, 0, vs->size, 0x1000, 0x10000, 0x20000000, &vs->mm); + if (ret) + kfree(vs->engdata); + return ret; +} + +void nv50_vspace_free(struct pscnv_vspace *vs) { + int i; + for (i = 0; i < NV50_VM_PDE_COUNT; i++) { + if (nv50_vs(vs)->pt[i]) { + pscnv_mem_free(nv50_vs(vs)->pt[i]); + } + } + kfree(vs->engdata); +} + +int nv50_vm_map_user(struct pscnv_bo *bo) { + struct drm_nouveau_private *dev_priv = bo->dev->dev_private; + struct nv50_vm_engine *vme = nv50_vm(dev_priv->vm); + if (bo->map1) + return 0; + return pscnv_vspace_map(vme->barvm, bo, 0, dev_priv->fb_size, 0, &bo->map1); +} + +int nv50_vm_map_kernel(struct pscnv_bo *bo) { + struct drm_nouveau_private *dev_priv = bo->dev->dev_private; + struct nv50_vm_engine *vme = nv50_vm(dev_priv->vm); + if (bo->map3) + return 0; + return pscnv_vspace_map(vme->barvm, bo, dev_priv->fb_size, dev_priv->fb_size + dev_priv->ramin_size, 0, &bo->map3); +} + +void +nv50_vm_bar_flush(struct drm_device *dev) { + nv_wr32(dev, 0x330c, 1); + if (!nouveau_wait_until(dev, 2000000000ULL, 0x330c, 2, 0)) { + NV_ERROR(dev, "BAR flush timeout!\n"); + } +} + +void +nv84_vm_bar_flush(struct drm_device *dev) { + nv_wr32(dev, 0x70000, 1); + if (!nouveau_wait_until(dev, 2000000000ULL, 0x70000, 2, 0)) { + NV_ERROR(dev, "BAR flush timeout!\n"); + } +} + +int +nv50_vm_init(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + int bar1dma, bar3dma; + struct nv50_vm_engine *vme = kzalloc(sizeof *vme, GFP_KERNEL); + if (!vme) { + NV_ERROR(dev, "VM: Couldn't alloc engine\n"); + return -ENOMEM; + } + vme->base.takedown = nv50_vm_takedown; + vme->base.do_vspace_new = nv50_vspace_new; + vme->base.do_vspace_free = nv50_vspace_free; + vme->base.place_map = nv50_vspace_place_map; + vme->base.do_map = nv50_vspace_do_map; + vme->base.do_unmap = nv50_vspace_do_unmap; + vme->base.map_user = nv50_vm_map_user; + vme->base.map_kernel = nv50_vm_map_kernel; + if (dev_priv->chipset == 0x50) + vme->base.bar_flush = nv50_vm_bar_flush; + else + vme->base.bar_flush = nv84_vm_bar_flush; + dev_priv->vm = &vme->base; + + dev_priv->vm_ramin_base = dev_priv->fb_size; + spin_lock_init(&dev_priv->vm->vs_lock); + + /* This is needed to get meaningful information from 100c90 + * on traps. No idea what these values mean exactly. */ + switch (dev_priv->chipset) { + case 0x50: + nv_wr32(dev, 0x100c90, 0x0707ff); + break; + case 0xa3: + case 0xa5: + case 0xa8: + case 0xaf: + nv_wr32(dev, 0x100c90, 0x0d0fff); + break; + default: + nv_wr32(dev, 0x100c90, 0x1d07ff); + break; + } + vme->barvm = pscnv_vspace_new (dev, dev_priv->fb_size + dev_priv->ramin_size, 0, 1); + if (!vme->barvm) { + kfree(vme); + dev_priv->vm = 0; + return -ENOMEM; + } + vme->barch = pscnv_chan_new (dev, vme->barvm, 1); + if (!vme->barch) { + pscnv_vspace_unref(vme->barvm); + kfree(vme); + dev_priv->vm = 0; + return -ENOMEM; + } + nv_wr32(dev, 0x1704, 0x40000000 | vme->barch->bo->start >> 12); + bar1dma = nv50_chan_dmaobj_new(vme->barch, 0x7fc00000, 0, dev_priv->fb_size); + bar3dma = nv50_chan_dmaobj_new(vme->barch, 0x7fc00000, dev_priv->fb_size, dev_priv->ramin_size); + nv_wr32(dev, 0x1708, 0x80000000 | bar1dma >> 4); + nv_wr32(dev, 0x170c, 0x80000000 | bar3dma >> 4); + dev_priv->vm_ok = 1; + nv50_vm_map_kernel(vme->barch->bo); + nv50_vm_map_kernel(nv50_vs(vme->barvm)->pt[0]); + return 0; +} + +void +nv50_vm_takedown(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv50_vm_engine *vme = nv50_vm(dev_priv->vm); + /* XXX: write me. */ + dev_priv->vm_ok = 0; + nv_wr32(dev, 0x1708, 0); + nv_wr32(dev, 0x170c, 0); + nv_wr32(dev, 0x1710, 0); + nv_wr32(dev, 0x1704, 0); + pscnv_chan_unref(vme->barch); + pscnv_vspace_unref(vme->barvm); + kfree(vme); + dev_priv->vm = 0; +} + +/* VM trap handling on NV50 is some kind of a fucking joke. + * + * So, there's this little bugger called MMU, which is in PFB area near + * 0x100c80 and contains registers to flush the TLB caches, and to report + * VM traps. + * + * And you have several units making use of that MMU. The known ones atm + * include PGRAPH, PFIFO, the BARs, and the PEEPHOLE. Each of these has its + * own TLBs. And most of them have several subunits, each having a separate + * MMU access path. + * + * Now, if you use an address that is bad in some way, the MMU responds "NO + * PAGE!!!11!1". And stores the relevant address + unit + channel into + * 0x100c90 area, where you can read it. However, it does NOT report an + * interrupt - this is done by the faulting unit. + * + * Now, if you get several page faults at once, which is not that uncommon + * if you fuck up something in your code, all but the first trap is lost. + * The unit reporting the trap may or may not also store the address on its + * own. + * + * So we report the trap in two pieces. First we go through all the possible + * faulters and report their status, which may range anywhere from full access + * info [like TPDMA] to just "oh! a trap!" [like VFETCH]. Then we ask the MMU + * for whatever trap it remembers. Then the user can look at dmesg and maybe + * match them using the MMU status field. Which we should decode someday, but + * meh for now. + * + * As for the Holy Grail of Demand Paging - hah. Who the hell knows. Given the + * fucked up reporting, the only hope lies in getting all individual units to + * cooperate. BAR accesses quite obviously cannot be demand paged [not a big + * problem - that's what host page tables are for]. PFIFO accesses all seem + * restartable just fine. As for PGRAPH... some, like TPDMA, are already dead + * when they happen, but maybe there's a DEBUG bit somewhere that changes it. + * Some others, like M2MF, hang on fault, and are therefore promising. But + * this requires shitloads of RE repeated for every unit. Have fun. + * + */ + +struct pscnv_enumval { + int value; + char *name; + void *data; +}; + +static struct pscnv_enumval vm_trap_reasons[] = { + { 0, "PT_NOT_PRESENT", 0}, + { 1, "PT_TOO_SHORT", 0 }, + { 2, "PAGE_NOT_PRESENT", 0 }, + { 3, "PAGE_SYSTEM_ONLY", 0 }, + { 4, "PAGE_READ_ONLY", 0 }, + /* 5 never seen */ + { 6, "NULL_DMAOBJ", 0 }, + { 7, "WRONG_MEMTYPE", 0 }, + /* 8-0xa never seen */ + { 0xb, "VRAM_LIMIT", 0 }, + /* 0xc-0xe never seen */ + { 0xf, "DMAOBJ_LIMIT", 0 }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_dispatch_subsubunits[] = { + { 0, "GRCTX", 0 }, + { 1, "NOTIFY", 0 }, + { 2, "QUERY", 0 }, + { 3, "COND", 0 }, + { 4, "M2M_IN", 0 }, + { 5, "M2M_OUT", 0 }, + { 6, "M2M_NOTIFY", 0 }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_ccache_subsubunits[] = { + { 0, "CB", 0 }, + { 1, "TIC", 0 }, + { 2, "TSC", 0 }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_tprop_subsubunits[] = { + { 0, "RT0", 0 }, + { 1, "RT1", 0 }, + { 2, "RT2", 0 }, + { 3, "RT3", 0 }, + { 4, "RT4", 0 }, + { 5, "RT5", 0 }, + { 6, "RT6", 0 }, + { 7, "RT7", 0 }, + { 8, "ZETA", 0 }, + { 9, "LOCAL", 0 }, + { 0xa, "GLOBAL", 0 }, + { 0xb, "STACK", 0 }, + { 0xc, "DST2D", 0 }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_pgraph_subunits[] = { + { 0, "STRMOUT", 0 }, + { 3, "DISPATCH", vm_dispatch_subsubunits }, + { 5, "CCACHE", vm_ccache_subsubunits }, + { 7, "CLIPID", 0 }, + { 9, "VFETCH", 0 }, + { 0xa, "TEXTURE", 0 }, + { 0xb, "TPROP", vm_tprop_subsubunits }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_crypt_subsubunits[] = { + { 0, "CRCTX", 0 }, + { 1, "SRC", 0 }, + { 2, "DST", 0 }, + { 3, "QUERY", 0 }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_pcrypt_subunits[] = { + { 0xe, "CRYPT", vm_crypt_subsubunits }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_pfifo_subsubunits[] = { + { 0, "PUSHBUF", 0 }, + { 1, "SEMAPHORE", 0 }, + /* 3 seen. also on semaphore. but couldn't reproduce. */ + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_pfifo_subunits[] = { + /* curious. */ + { 8, "FIFO", vm_pfifo_subsubunits }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_peephole_subunits[] = { + /* even more curious. */ + { 4, "WRITE", 0 }, + { 8, "READ", 0 }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_bar_subsubunits[] = { + { 0, "FB", 0 }, + { 1, "IN", 0 }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_bar_subunits[] = { + /* even more curious. */ + { 4, "WRITE", vm_bar_subsubunits }, + { 8, "READ", vm_bar_subsubunits }, + /* 0xa also seen. some kind of write. */ + { 0, 0, 0 }, +}; + +static struct pscnv_enumval vm_units[] = { + { 0, "PGRAPH", vm_pgraph_subunits }, + { 1, "PVP", 0 }, + /* 2, 3 never seen */ + { 4, "PEEPHOLE", vm_peephole_subunits }, + { 5, "PFIFO", vm_pfifo_subunits }, + { 6, "BAR", vm_bar_subunits }, + /* 7 never seen */ + { 8, "PPPP", 0 }, + { 9, "PBSP", 0 }, + { 0xa, "PCRYPT", vm_pcrypt_subunits }, + /* 0xb, 0xc never seen */ + { 0xd, "PCOPY", 0 }, + { 0xe, "PDAEMON", 0 }, + { 0, 0, 0 }, +}; + +static struct pscnv_enumval *pscnv_enum_find (struct pscnv_enumval *list, int val) { + while (list->value != val && list->name) + list++; + if (list->name) + return list; + else + return 0; +} + +void nv50_vm_trap(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t trap[6]; + int i; + uint32_t idx = nv_rd32(dev, 0x100c90); + uint32_t s0, s1, s2, s3; + char reason[50]; + char unit1[50]; + char unit2[50]; + char unit3[50]; + struct pscnv_enumval *ev; + int chan; + if (idx & 0x80000000) { + idx &= 0xffffff; + for (i = 0; i < 6; i++) { + nv_wr32(dev, 0x100c90, idx | i << 24); + trap[i] = nv_rd32(dev, 0x100c94); + } + if (dev_priv->chipset < 0xa3 || (dev_priv->chipset >= 0xaa && dev_priv->chipset <= 0xac)) { + s0 = trap[0] & 0xf; + s1 = (trap[0] >> 4) & 0xf; + s2 = (trap[0] >> 8) & 0xf; + s3 = (trap[0] >> 12) & 0xf; + } else { + s0 = trap[0] & 0xff; + s1 = (trap[0] >> 8) & 0xff; + s2 = (trap[0] >> 16) & 0xff; + s3 = (trap[0] >> 24) & 0xff; + } + ev = pscnv_enum_find(vm_trap_reasons, s1); + if (ev) + snprintf(reason, sizeof(reason), "%s", ev->name); + else + snprintf(reason, sizeof(reason), "0x%x", s1); + ev = pscnv_enum_find(vm_units, s0); + if (ev) + snprintf(unit1, sizeof(unit1), "%s", ev->name); + else + snprintf(unit1, sizeof(unit1), "0x%x", s0); + if (ev && (ev = ev->data) && (ev = pscnv_enum_find(ev, s2))) + snprintf(unit2, sizeof(unit2), "%s", ev->name); + else + snprintf(unit2, sizeof(unit2), "0x%x", s2); + if (ev && (ev = ev->data) && (ev = pscnv_enum_find(ev, s3))) + snprintf(unit3, sizeof(unit3), "%s", ev->name); + else + snprintf(unit3, sizeof(unit3), "0x%x", s3); + chan = pscnv_chan_handle_lookup(dev, trap[2] << 16 | trap[1]); + if (chan != 128) { + NV_INFO(dev, "VM: Trapped %s at %02x%04x%04x ch %d on %s/%s/%s, reason %s\n", + (trap[5]&0x100?"read":"write"), + trap[5]&0xff, trap[4]&0xffff, + trap[3]&0xffff, chan, unit1, unit2, unit3, reason); + } else { + NV_INFO(dev, "VM: Trapped %s at %02x%04x%04x UNKNOWN ch %08x on %s/%s/%s, reason %s\n", + (trap[5]&0x100?"read":"write"), + trap[5]&0xff, trap[4]&0xffff, + trap[3]&0xffff, trap[2] << 16 | trap[1], unit1, unit2, unit3, reason); + } + nv_wr32(dev, 0x100c90, idx | 0x80000000); + } +} diff --git a/driver/pscnv/nv50_vm.h b/driver/pscnv/nv50_vm.h new file mode 100644 index 00000000..a0908a5a --- /dev/null +++ b/driver/pscnv/nv50_vm.h @@ -0,0 +1,31 @@ +#ifndef __NV50_VM_H__ +#define __NV50_VM_H__ + +#include "drmP.h" +#include "drm.h" +#include "pscnv_vm.h" + +#define NV50_VM_SIZE 0x10000000000ULL +#define NV50_VM_PDE_COUNT 0x800 +#define NV50_VM_SPTE_COUNT 0x20000 +#define NV50_VM_LPTE_COUNT 0x2000 + +#define nv50_vm(x) container_of(x, struct nv50_vm_engine, base) +#define nv50_vs(x) ((struct nv50_vspace *)(x)->engdata) + +struct nv50_vm_engine { + struct pscnv_vm_engine base; + struct pscnv_vspace *barvm; + struct pscnv_chan *barch; +}; + +struct nv50_vspace { + struct list_head chan_list; + int engref[PSCNV_ENGINES_NUM]; + struct pscnv_bo *pt[NV50_VM_PDE_COUNT]; +}; + +int nv50_vm_flush (struct drm_device *dev, int unit); +void nv50_vm_trap(struct drm_device *dev); + +#endif /* __NV50_VM_H__ */ diff --git a/driver/pscnv/nv50_vram.c b/driver/pscnv/nv50_vram.c new file mode 100644 index 00000000..3fc97e42 --- /dev/null +++ b/driver/pscnv/nv50_vram.c @@ -0,0 +1,285 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "pscnv_mem.h" + +int nv50_vram_alloc(struct pscnv_bo *bo); +int nv50_sysram_tiling_ok(struct pscnv_bo *bo); + +int +nv50_vram_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t r0, r4, rc, ru, rt; + int parts, i, colbits, rowbitsa, rowbitsb, banks; + uint64_t rowsize, predicted; + uint32_t rblock_size; + int ret; + + dev_priv->vram = kzalloc (sizeof *dev_priv->vram, GFP_KERNEL); + if (!dev_priv->vram) { + NV_ERROR(dev, "VRAM: out ot memory\n"); + return -ENOMEM; + } + + dev_priv->vram->alloc = nv50_vram_alloc; + dev_priv->vram->free = pscnv_vram_free; + dev_priv->vram->takedown = pscnv_vram_takedown; + dev_priv->vram->sysram_tiling_ok = nv50_sysram_tiling_ok; + + if (dev_priv->chipset == 0xaa || dev_priv->chipset == 0xac || dev_priv->chipset == 0xaf) { + rc = nv_rd32(dev, 0x10020c); + dev_priv->vram_sys_base = (uint64_t)nv_rd32(dev, 0x100e10) << 12; + dev_priv->vram_size = (rc & 0xfffff000) | ((uint64_t)rc & 0xff) << 32; + rblock_size = 0x1000; + + NV_INFO(dev, "VRAM: IGP stolen area at %llx size 0x%llx", + dev_priv->vram_sys_base, dev_priv->vram_size); + } else { + dev_priv->vram_sys_base = 0; + + r0 = nv_rd32(dev, 0x100200); + r4 = nv_rd32(dev, 0x100204); + rc = nv_rd32(dev, 0x10020c); + rt = nv_rd32(dev, 0x100250); + ru = nv_rd32(dev, 0x1540); + NV_INFO (dev, "Memory config regs: %08x %08x %08x %08x %08x\n", r0, r4, rc, rt, ru); + + parts = 0; + for (i = 0; i < 8; i++) + if (ru & (1 << (i + 16))) + parts++; + colbits = (r4 >> 12) & 0xf; + rowbitsa = ((r4 >> 16) & 0xf) + 8; + rowbitsb = ((r4 >> 20) & 0xf) + 8; + banks = ((r4 & 1 << 24) ? 8 : 4); + rowsize = parts * banks * (1 << colbits) * 8; + predicted = rowsize << rowbitsa; + if (r0 & 4) + predicted += rowsize << rowbitsb; + + dev_priv->vram_size = (rc & 0xfffff000) | ((uint64_t)rc & 0xff) << 32; + if (!dev_priv->vram_size) { + NV_ERROR(dev, "Memory controller claims 0 VRAM - aborting.\n"); + kfree(dev_priv->vram); + return -ENODEV; + } + if (dev_priv->vram_size != predicted) { + NV_WARN(dev, "Memory controller reports VRAM size of 0x%llx, inconsistent with our calculation of 0x%llx!\n", dev_priv->vram_size, predicted); + } + + /* XXX: 100250 has more bits. check what they do some day. */ + if (rt & 1) + rblock_size = rowsize * 3; + else + rblock_size = rowsize; + + NV_INFO(dev, "VRAM: size 0x%llx, LSR period %x\n", + dev_priv->vram_size, rblock_size); + } + + ret = pscnv_mm_init(dev, 0x40000, dev_priv->vram_size - 0x20000, 0x1000, 0x10000, rblock_size, &dev_priv->vram_mm); + if (ret) { + kfree(dev_priv->vram); + return ret; + } + + return 0; +} + +int +nv50_sysram_tiling_ok(struct pscnv_bo *bo) { + switch (bo->tile_flags) { + case 0: + case 0x10: + case 0x11: + case 0x12: + case 0x13: + case 0x20: + case 0x21: + case 0x22: + case 0x23: + case 0x24: + case 0x25: + case 0x26: + case 0x40: + case 0x41: + case 0x42: + case 0x43: + case 0x44: + case 0x45: + case 0x46: + case 0x54: + case 0x55: + case 0x56: + case 0x60: + case 0x61: + case 0x62: + case 0x63: + case 0x64: + case 0x65: + case 0x66: + case 0x68: + case 0x69: + case 0x6a: + case 0x6b: + case 0x70: + case 0x74: + case 0x78: + case 0x79: + case 0x7c: + case 0x7d: + case 0x18: + case 0x19: + case 0x1a: + case 0x1b: + case 0x28: + case 0x29: + case 0x2a: + case 0x2b: + case 0x2c: + case 0x2d: + case 0x2e: + case 0x47: + case 0x48: + case 0x49: + case 0x4a: + case 0x4b: + case 0x4c: + case 0x4d: + case 0x6c: + case 0x6d: + case 0x6e: + case 0x6f: + case 0x72: + case 0x76: + case 0x7a: + case 0x7b: + return 1; + default: + return 0; + } +} + +int +nv50_vram_alloc(struct pscnv_bo *bo) +{ + struct drm_device *dev = bo->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + int flags, ret; + switch (bo->tile_flags) { + case 0: + case 0x10: + case 0x11: + case 0x12: + case 0x13: + case 0x20: + case 0x21: + case 0x22: + case 0x23: + case 0x24: + case 0x25: + case 0x26: + case 0x40: + case 0x41: + case 0x42: + case 0x43: + case 0x44: + case 0x45: + case 0x46: + case 0x54: + case 0x55: + case 0x56: + case 0x60: + case 0x61: + case 0x62: + case 0x63: + case 0x64: + case 0x65: + case 0x66: + case 0x68: + case 0x69: + case 0x6a: + case 0x6b: + case 0x70: + case 0x74: + case 0x78: + case 0x79: + case 0x7c: + case 0x7d: + flags = 0; + break; + case 0x18: + case 0x19: + case 0x1a: + case 0x1b: + case 0x28: + case 0x29: + case 0x2a: + case 0x2b: + case 0x2c: + case 0x2d: + case 0x2e: + case 0x47: + case 0x48: + case 0x49: + case 0x4a: + case 0x4b: + case 0x4c: + case 0x4d: + case 0x6c: + case 0x6d: + case 0x6e: + case 0x6f: + case 0x72: + case 0x76: + case 0x7a: + case 0x7b: + flags = PSCNV_MM_T1 | PSCNV_MM_FROMBACK; + break; + default: + return -EINVAL; + } + bo->size = roundup(bo->size, 0x1000); + if ((bo->flags & PSCNV_GEM_MEMTYPE_MASK) == PSCNV_GEM_VRAM_LARGE) { + flags |= PSCNV_MM_LP; + bo->size = roundup(bo->size, 0x10000); + } + if (!(bo->flags & PSCNV_GEM_CONTIG)) + flags |= PSCNV_MM_FRAGOK; + mutex_lock(&dev_priv->vram_mutex); + ret = pscnv_mm_alloc(dev_priv->vram_mm, bo->size, flags, 0, dev_priv->vram_size, &bo->mmnode); + if (!ret) { + if (bo->flags & PSCNV_GEM_CONTIG) + bo->start = bo->mmnode->start; + bo->mmnode->tag = bo; + } + mutex_unlock(&dev_priv->vram_mutex); + return ret; +} diff --git a/driver/pscnv/nv84_crypt.c b/driver/pscnv/nv84_crypt.c new file mode 100644 index 00000000..315e0657 --- /dev/null +++ b/driver/pscnv/nv84_crypt.c @@ -0,0 +1,264 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drm.h" +#include "drmP.h" +#include "nouveau_drv.h" +#include "pscnv_engine.h" +#include "pscnv_chan.h" +#include "nv50_chan.h" +#include "nv50_vm.h" + +struct nv84_crypt_engine { + struct pscnv_engine base; + spinlock_t lock; +}; + +struct nv84_crypt_chan { + struct pscnv_bo *crctx; +}; + +#define nv84_crypt(x) container_of(x, struct nv84_crypt_engine, base) + +static int nv84_crypt_oclasses[] = { + 0x74c1, + 0 +}; + +void nv84_crypt_takedown(struct pscnv_engine *eng); +void nv84_crypt_irq_handler(struct drm_device *dev, int irq); +int nv84_crypt_tlb_flush(struct pscnv_engine *eng, struct pscnv_vspace *vs); +int nv86_crypt_tlb_flush(struct pscnv_engine *eng, struct pscnv_vspace *vs); +int nv84_crypt_chan_alloc(struct pscnv_engine *eng, struct pscnv_chan *ch); +void nv84_crypt_chan_free(struct pscnv_engine *eng, struct pscnv_chan *ch); +void nv84_crypt_chan_kill(struct pscnv_engine *eng, struct pscnv_chan *ch); +int nv84_crypt_chan_obj_new(struct pscnv_engine *eng, struct pscnv_chan *ch, uint32_t handle, uint32_t oclass, uint32_t flags); + +int nv84_crypt_init(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv84_crypt_engine *res = kzalloc(sizeof *res, GFP_KERNEL); + + if (!res) { + NV_ERROR(dev, "PCRYPT: Couldn't allocate engine!\n"); + return -ENOMEM; + } + + res->base.dev = dev; + res->base.oclasses = nv84_crypt_oclasses; + res->base.takedown = nv84_crypt_takedown; + res->base.tlb_flush = nv84_crypt_tlb_flush; + res->base.chan_alloc = nv84_crypt_chan_alloc; + res->base.chan_kill = nv84_crypt_chan_kill; + res->base.chan_free = nv84_crypt_chan_free; + res->base.chan_obj_new = nv84_crypt_chan_obj_new; + spin_lock_init(&res->lock); + + /* reset everything */ + nv_wr32(dev, 0x200, 0xffffbfff); + nv_wr32(dev, 0x200, 0xffffffff); + + nv_wr32(dev, 0x102130, -1); /* INTR */ + +#if 0 + nv_wr32(dev, 0x102080, 0x3150a); + nv_wr32(dev, 0x10208c, 0x40f00f); + nv_wr32(dev, 0x10208c, 0x40f007); + nv_wr32(dev, 0x102300, 0x63); + nv_wr32(dev, 0x102304, 0xf0000); + nv_wr32(dev, 0x102308, 4); + nv_wr32(dev, 0x10232c, 0x8010ffac); + nv_wr32(dev, 0x102084, 0x10300); +#endif + + /* enable FIFO access */ + nv_wr32(dev, 0x10200c, 0x10); + +#if 0 + /* mark no channel loaded */ + nv_wr32(dev, 0x102188, 0); + nv_wr32(dev, 0x10218c, 0); +#endif + + dev_priv->engines[PSCNV_ENGINE_CRYPT] = &res->base; + + nouveau_irq_register(dev, 14, nv84_crypt_irq_handler); + + nv_wr32(dev, 0x102140, 0x18f); /* INTR_EN */ + return 0; +} + +void nv84_crypt_takedown(struct pscnv_engine *eng) { + struct drm_nouveau_private *dev_priv = eng->dev->dev_private; + nv_wr32(eng->dev, 0x102140, 0); /* INTR_EN */ + nouveau_irq_unregister(eng->dev, 14); + /* XXX */ + kfree(eng); + dev_priv->engines[PSCNV_ENGINE_CRYPT] = 0; +} + +int nv84_crypt_chan_alloc(struct pscnv_engine *eng, struct pscnv_chan *ch) { + struct drm_device *dev = eng->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t hdr; + uint64_t limit; + int i; + struct nv84_crypt_chan *crch = kzalloc(sizeof *crch, GFP_KERNEL); + + if (!crch) { + NV_ERROR(dev, "PCRYPT: Couldn't allocate channel!\n"); + return -ENOMEM; + } + + hdr = 0xa0; + crch->crctx = pscnv_mem_alloc(dev, 0x100, PSCNV_GEM_CONTIG, 0, 0xc7c07e47); + if (!crch->crctx) { + NV_ERROR(dev, "PCRYPT: No VRAM for context!\n"); + kfree(crch); + return -ENOMEM; + } + for (i = 0; i < 0x100; i += 4) + nv_wv32(crch->crctx, i, 0); + limit = crch->crctx->start + 0x100 - 1; + + nv_wv32(ch->bo, hdr + 0x00, 0x00190000); + nv_wv32(ch->bo, hdr + 0x04, limit); + nv_wv32(ch->bo, hdr + 0x08, crch->crctx->start); + nv_wv32(ch->bo, hdr + 0x0c, (limit >> 32) << 24 | (crch->crctx->start >> 32)); + nv_wv32(ch->bo, hdr + 0x10, 0); + nv_wv32(ch->bo, hdr + 0x14, 0); + dev_priv->vm->bar_flush(dev); + + nv50_vs(ch->vspace)->engref[PSCNV_ENGINE_CRYPT]++; + ch->engdata[PSCNV_ENGINE_CRYPT] = crch; + return 0; +} + +int nv84_crypt_tlb_flush(struct pscnv_engine *eng, struct pscnv_vspace *vs) { + return nv50_vm_flush(eng->dev, 0xa); +} + +void nv84_crypt_chan_kill(struct pscnv_engine *eng, struct pscnv_chan *ch) { + struct drm_device *dev = eng->dev; + struct nv84_crypt_engine *crypt = nv84_crypt(eng); + unsigned long flags; + spin_lock_irqsave(&crypt->lock, flags); + /* disable PFIFO access */ + nv_wr32(dev, 0x10200c, 0); + /* check if the channel we're freeing is active on PCRYPT. */ + if (nv_rd32(dev, 0x102188) == (0x80000000 | ch->bo->start >> 12)) { + NV_INFO(dev, "Kicking channel %d off PCRYPT.\n", ch->cid); + nv_wr32(dev, 0x102188, 0); + } + /* or maybe it was just going to be loaded in? */ + if (nv_rd32(dev, 0x10218c) == (0x80000000 | ch->bo->start >> 12)) { + nv_wr32(dev, 0x10218c, 0); + } + /* back to normal state. */ + nv_wr32(dev, 0x10200c, 0x10); + spin_unlock_irqrestore(&crypt->lock, flags); +} + +void nv84_crypt_chan_free(struct pscnv_engine *eng, struct pscnv_chan *ch) { + struct nv84_crypt_chan *crch = ch->engdata[PSCNV_ENGINE_CRYPT]; + pscnv_mem_free(crch->crctx); + kfree(crch); + nv50_vs(ch->vspace)->engref[PSCNV_ENGINE_CRYPT]--; + ch->engdata[PSCNV_ENGINE_CRYPT] = 0; + nv84_crypt_tlb_flush(eng, ch->vspace); +} + +int nv84_crypt_chan_obj_new(struct pscnv_engine *eng, struct pscnv_chan *ch, uint32_t handle, uint32_t oclass, uint32_t flags) { + uint32_t inst = nv50_chan_iobj_new(ch, 0x20); + if (!inst) { + return -ENOMEM; + } + nv_wv32(ch->bo, inst, oclass); + nv_wv32(ch->bo, inst + 4, 0); + nv_wv32(ch->bo, inst + 8, 0); + nv_wv32(ch->bo, inst + 0xc, 0); + nv_wv32(ch->bo, inst + 0x10, 0); + nv_wv32(ch->bo, inst + 0x14, 0); + nv_wv32(ch->bo, inst + 0x18, 0); + nv_wv32(ch->bo, inst + 0x1c, 0); + return pscnv_ramht_insert (&ch->ramht, handle, 0x500000 | inst >> 4); +} + +void nv84_crypt_irq_handler(struct drm_device *dev, int irq) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv84_crypt_engine *crypt = nv84_crypt(dev_priv->engines[PSCNV_ENGINE_CRYPT]); + uint32_t status; + unsigned long flags; + uint32_t chandle, data, mthd; + int cid; + spin_lock_irqsave(&crypt->lock, flags); + status = nv_rd32(dev, 0x102130); + mthd = nv_rd32(dev, 0x102190); + data = nv_rd32(dev, 0x102194); + chandle = nv_rd32(dev, 0x102188) & 0x7fffffff; + cid = pscnv_chan_handle_lookup(dev, chandle); + if (cid == 128) { + NV_ERROR(dev, "PCRYPT: UNKNOWN channel %x active!\n", chandle); + } + + if (status & 1) { + NV_ERROR(dev, "PCRYPT_INVALID_STATE: ch %d mthd %04x data %08x\n", cid, mthd, data); + nv_wr32(dev, 0x102130, 1); + status &= ~1; + } + + if (status & 2) { + NV_ERROR(dev, "PCRYPT_ILLEGAL_MTHD: ch %d mthd %04x data %08x\n", cid, mthd, data); + nv_wr32(dev, 0x102130, 2); + status &= ~2; + } + + if (status & 4) { + NV_ERROR(dev, "PCRYPT_ILLEGAL_CLASS: ch %d mthd %04x data %08x\n", cid, mthd, data); + nv_wr32(dev, 0x102130, 4); + status &= ~4; + } + + if (status & 0x80) { + NV_ERROR(dev, "PCRYPT_QUERY: ch %d mthd %04x data %08x\n", cid, mthd, data); + nv_wr32(dev, 0x102130, 0x80); + status &= ~0x80; + } + + if (status & 0x100) { + NV_ERROR(dev, "PCRYPT_FAULT: ch %d mthd %04x data %08x\n", cid, mthd, data); + nv_wr32(dev, 0x102130, 0x100); + status &= ~0x100; + } + + if (status) { + NV_ERROR(dev, "Unknown PCRYPT interrupt %08x\n", status); + NV_ERROR(dev, "PCRYPT: ch %d mthd %04x data %08x\n", cid, mthd, data); + nv_wr32(dev, 0x102130, status); + } + nv50_vm_trap(dev); + nv_wr32(dev, 0x10200c, 0x10); + spin_unlock_irqrestore(&crypt->lock, flags); +} diff --git a/driver/pscnv/nv98_crypt.c b/driver/pscnv/nv98_crypt.c new file mode 100644 index 00000000..f938da53 --- /dev/null +++ b/driver/pscnv/nv98_crypt.c @@ -0,0 +1,258 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drm.h" +#include "drmP.h" +#include "nouveau_drv.h" +#include "pscnv_engine.h" +#include "pscnv_chan.h" +#include "nv50_chan.h" +#include "nv50_vm.h" +#include "nv98_crypt.fuc.h" + +struct nv98_crypt_engine { + struct pscnv_engine base; + spinlock_t lock; +}; + +struct nv98_crypt_chan { + struct pscnv_bo *crctx; +}; + +#define nv98_crypt(x) container_of(x, struct nv98_crypt_engine, base) + +static int nv98_crypt_oclasses[] = { + 0x88f4, + 0 +}; + +void nv98_crypt_takedown(struct pscnv_engine *eng); +void nv98_crypt_irq_handler(struct drm_device *dev, int irq); +int nv98_crypt_tlb_flush(struct pscnv_engine *eng, struct pscnv_vspace *vs); +int nv86_crypt_tlb_flush(struct pscnv_engine *eng, struct pscnv_vspace *vs); +int nv98_crypt_chan_alloc(struct pscnv_engine *eng, struct pscnv_chan *ch); +void nv98_crypt_chan_free(struct pscnv_engine *eng, struct pscnv_chan *ch); +void nv98_crypt_chan_kill(struct pscnv_engine *eng, struct pscnv_chan *ch); +int nv98_crypt_chan_obj_new(struct pscnv_engine *eng, struct pscnv_chan *ch, uint32_t handle, uint32_t oclass, uint32_t flags); + +int nv98_crypt_init(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv98_crypt_engine *res = kzalloc(sizeof *res, GFP_KERNEL); + int i; + + if (!res) { + NV_ERROR(dev, "PCRYPT: Couldn't allocate engine!\n"); + return -ENOMEM; + } + + res->base.dev = dev; + res->base.oclasses = nv98_crypt_oclasses; + res->base.takedown = nv98_crypt_takedown; + res->base.tlb_flush = nv98_crypt_tlb_flush; + res->base.chan_alloc = nv98_crypt_chan_alloc; + res->base.chan_kill = nv98_crypt_chan_kill; + res->base.chan_free = nv98_crypt_chan_free; + res->base.chan_obj_new = nv98_crypt_chan_obj_new; + spin_lock_init(&res->lock); + + /* reset everything */ + nv_wr32(dev, 0x200, 0xffffbfff); + nv_wr32(dev, 0x200, 0xffffffff); + + while (!(nv_rd32(dev, 0x87008) & 0x10)); + nv_wr32(dev, 0x87004, 0x10); + + nv_wr32(dev, 0x87ff8, 0x00100000); + for (i = 0; i < sizeof(nv98_pcrypt_code); i += 4) + nv_wr32(dev, 0x87ff4, nv98_pcrypt_code[i] | nv98_pcrypt_code[i+1] << 8 | nv98_pcrypt_code[i+2] << 16 | nv98_pcrypt_code[i+3] << 24); + nv_wr32(dev, 0x87ff8, 0x00000000); + for (i = 0; i < sizeof(nv98_pcrypt_data); i += 4) + nv_wr32(dev, 0x87ff4, nv98_pcrypt_data[i] | nv98_pcrypt_data[i+1] << 8 | nv98_pcrypt_data[i+2] << 16 | nv98_pcrypt_data[i+3] << 24); + + dev_priv->engines[PSCNV_ENGINE_CRYPT] = &res->base; + + nouveau_irq_register(dev, 14, nv98_crypt_irq_handler); + + nv_wr32(dev, 0x8710c, 0); + nv_wr32(dev, 0x87104, 0); /* ENTRY */ + nv_wr32(dev, 0x87100, 2); /* TRIGGER */ + return 0; +} + +void nv98_crypt_takedown(struct pscnv_engine *eng) { + struct drm_nouveau_private *dev_priv = eng->dev->dev_private; + nv_wr32(eng->dev, 0x87014, -1); /* INTR_EN */ + nouveau_irq_unregister(eng->dev, 14); + /* XXX */ + kfree(eng); + dev_priv->engines[PSCNV_ENGINE_CRYPT] = 0; +} + +int nv98_crypt_chan_alloc(struct pscnv_engine *eng, struct pscnv_chan *ch) { + struct drm_device *dev = eng->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + uint32_t hdr; + uint64_t limit; + int i; + struct nv98_crypt_chan *crch = kzalloc(sizeof *crch, GFP_KERNEL); + + if (!crch) { + NV_ERROR(dev, "PCRYPT: Couldn't allocate channel!\n"); + return -ENOMEM; + } + + hdr = 0xa0; + crch->crctx = pscnv_mem_alloc(dev, 0x100, PSCNV_GEM_CONTIG, 0, 0xc7c07e47); + if (!crch->crctx) { + NV_ERROR(dev, "PCRYPT: No VRAM for context!\n"); + kfree(crch); + return -ENOMEM; + } + for (i = 0; i < 0x100; i += 4) + nv_wv32(crch->crctx, i, 0); + limit = crch->crctx->start + 0x80 - 1; + + nv_wv32(ch->bo, hdr + 0x00, 0x00190000); + nv_wv32(ch->bo, hdr + 0x04, limit); + nv_wv32(ch->bo, hdr + 0x08, crch->crctx->start); + nv_wv32(ch->bo, hdr + 0x0c, (limit >> 32) << 24 | (crch->crctx->start >> 32)); + nv_wv32(ch->bo, hdr + 0x10, 0); + nv_wv32(ch->bo, hdr + 0x14, 0); + dev_priv->vm->bar_flush(dev); + + nv50_vs(ch->vspace)->engref[PSCNV_ENGINE_CRYPT]++; + ch->engdata[PSCNV_ENGINE_CRYPT] = crch; + return 0; +} + +int nv98_crypt_tlb_flush(struct pscnv_engine *eng, struct pscnv_vspace *vs) { + return nv50_vm_flush(eng->dev, 0xa); +} + +void nv98_crypt_chan_kill(struct pscnv_engine *eng, struct pscnv_chan *ch) { + struct drm_device *dev = eng->dev; + struct nv98_crypt_engine *crypt = nv98_crypt(eng); + unsigned long flags; + spin_lock_irqsave(&crypt->lock, flags); + /* disable PFIFO access */ + nv_wr32(dev, 0x87048, 0); + /* check if the channel we're freeing is active on PCRYPT. */ + if (nv_rd32(dev, 0x87050) == (0x40000000 | ch->bo->start >> 12)) { + NV_INFO(dev, "Kicking channel %d off PCRYPT.\n", ch->cid); + nv_wr32(dev, 0x87050, 0); + } + /* or maybe it was just going to be loaded in? */ + if (nv_rd32(dev, 0x87054) == (0x40000000 | ch->bo->start >> 12)) { + nv_wr32(dev, 0x87054, 0); + } + /* back to normal state. */ + nv_wr32(dev, 0x87048, 0x3); + spin_unlock_irqrestore(&crypt->lock, flags); +} + +void nv98_crypt_chan_free(struct pscnv_engine *eng, struct pscnv_chan *ch) { + struct nv98_crypt_chan *crch = ch->engdata[PSCNV_ENGINE_CRYPT]; + pscnv_mem_free(crch->crctx); + kfree(crch); + nv50_vs(ch->vspace)->engref[PSCNV_ENGINE_CRYPT]--; + ch->engdata[PSCNV_ENGINE_CRYPT] = 0; + nv98_crypt_tlb_flush(eng, ch->vspace); +} + +int nv98_crypt_chan_obj_new(struct pscnv_engine *eng, struct pscnv_chan *ch, uint32_t handle, uint32_t oclass, uint32_t flags) { + uint32_t inst = nv50_chan_iobj_new(ch, 0x20); + if (!inst) { + return -ENOMEM; + } + nv_wv32(ch->bo, inst, oclass); + nv_wv32(ch->bo, inst + 4, 0); + nv_wv32(ch->bo, inst + 8, 0); + nv_wv32(ch->bo, inst + 0xc, 0); + nv_wv32(ch->bo, inst + 0x10, 0); + nv_wv32(ch->bo, inst + 0x14, 0); + nv_wv32(ch->bo, inst + 0x18, 0); + nv_wv32(ch->bo, inst + 0x1c, 0); + return pscnv_ramht_insert (&ch->ramht, handle, 0x500000 | inst >> 4); +} + +void nv98_crypt_irq_handler(struct drm_device *dev, int irq) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nv98_crypt_engine *crypt = nv98_crypt(dev_priv->engines[PSCNV_ENGINE_CRYPT]); + uint32_t status, dispatch; + unsigned long flags; + uint32_t chandle, data, addr, subc, mthd, ecode; + int cid; + spin_lock_irqsave(&crypt->lock, flags); + dispatch = nv_rd32(dev, 0x8701c); + status = nv_rd32(dev, 0x87008) & dispatch & ~(dispatch >> 16); + addr = nv_rd32(dev, 0x87040) >> 16; + ecode = nv_rd32(dev, 0x87040) & 0xffff; + + data = nv_rd32(dev, 0x87044); + mthd = addr << 2 & 0x1ffc; + subc = addr >> 11 & 7; + chandle = nv_rd32(dev, 0x87050) & 0x3fffffff; + cid = pscnv_chan_handle_lookup(dev, chandle); + if (cid == 128) { + NV_ERROR(dev, "PCRYPT: UNKNOWN channel %x active!\n", chandle); + } + + if (status & 0x40) { + switch (ecode) { + case 0: + NV_ERROR(dev, "PCRYPT_ILLEGAL_MTHD: ch %d subc %d mthd %04x data %08x\n", cid, subc, mthd, data); + break; + case 1: + NV_ERROR(dev, "PCRYPT_INVALID_BITFIELD: ch %d subc %d mthd %04x data %08x\n", cid, subc, mthd, data); + break; + case 2: + NV_ERROR(dev, "PCRYPT_INVALID_ENUM: ch %d subc %d mthd %04x data %08x\n", cid, subc, mthd, data); + break; + case 3: + NV_ERROR(dev, "PCRYPT_QUERY: ch %d subc %d mthd %04x data %08x\n", cid, subc, mthd, data); + break; + default: + NV_ERROR(dev, "PCRYPT_DISPATCH_ERROR [%x]: ch %d subc %d mthd %04x data %08x\n", ecode, cid, subc, mthd, data); + break; + } + nv_wr32(dev, 0x87004, 0x40); + status &= ~0x40; + } + + if (status & 0x200) { + NV_ERROR(dev, "PCRYPT_FAULT: ch %d\n", cid); + nv_wr32(dev, 0x87004, 0x200); + status &= ~0x200; + } + + if (status) { + NV_ERROR(dev, "Unknown PCRYPT interrupt %08x\n", status); + NV_ERROR(dev, "PCRYPT: ch %d\n", cid); + nv_wr32(dev, 0x87004, status); + } + nv50_vm_trap(dev); + spin_unlock_irqrestore(&crypt->lock, flags); +} diff --git a/driver/pscnv/nv98_crypt.fuc b/driver/pscnv/nv98_crypt.fuc new file mode 100644 index 00000000..a4e12ae1 --- /dev/null +++ b/driver/pscnv/nv98_crypt.fuc @@ -0,0 +1,699 @@ +/* + * fuc microcode for nv98 pcrypt engine + * Copyright (C) 2010 Marcin Kościelnicki + * + * This program 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, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +.section #nv98_pcrypt_data + +ctx_dma: +ctx_dma_query: .b32 0 +ctx_dma_src: .b32 0 +ctx_dma_dst: .b32 0 +.equ #dma_count 3 +ctx_query_address_high: .b32 0 +ctx_query_address_low: .b32 0 +ctx_query_counter: .b32 0 +ctx_cond_address_high: .b32 0 +ctx_cond_address_low: .b32 0 +ctx_cond_off: .b32 0 +ctx_src_address_high: .b32 0 +ctx_src_address_low: .b32 0 +ctx_dst_address_high: .b32 0 +ctx_dst_address_low: .b32 0 +ctx_mode: .b32 0 +.align 16 +ctx_key: .skip 16 +ctx_iv: .skip 16 + +.align 0x80 +swap: +.skip 32 + +.align 8 +common_cmd_dtable: +.b32 #ctx_query_address_high + 0x20000 ~0xff +.b32 #ctx_query_address_low + 0x20000 ~0xfffffff0 +.b32 #ctx_query_counter + 0x20000 ~0xffffffff +.b32 #cmd_query_get + 0x00000 ~1 +.b32 #ctx_cond_address_high + 0x20000 ~0xff +.b32 #ctx_cond_address_low + 0x20000 ~0xfffffff0 +.b32 #cmd_cond_mode + 0x00000 ~7 +.b32 #cmd_wrcache_flush + 0x00000 ~0 +.equ #common_cmd_max 0x88 + + +.align 8 +engine_cmd_dtable: +.b32 #ctx_key + 0x0 + 0x20000 ~0xffffffff +.b32 #ctx_key + 0x4 + 0x20000 ~0xffffffff +.b32 #ctx_key + 0x8 + 0x20000 ~0xffffffff +.b32 #ctx_key + 0xc + 0x20000 ~0xffffffff +.b32 #ctx_iv + 0x0 + 0x20000 ~0xffffffff +.b32 #ctx_iv + 0x4 + 0x20000 ~0xffffffff +.b32 #ctx_iv + 0x8 + 0x20000 ~0xffffffff +.b32 #ctx_iv + 0xc + 0x20000 ~0xffffffff +.b32 #ctx_src_address_high + 0x20000 ~0xff +.b32 #ctx_src_address_low + 0x20000 ~0xfffffff0 +.b32 #ctx_dst_address_high + 0x20000 ~0xff +.b32 #ctx_dst_address_low + 0x20000 ~0xfffffff0 +.b32 #crypt_cmd_mode + 0x00000 ~0xf +.b32 #crypt_cmd_length + 0x10000 ~0x0ffffff0 +.equ #engine_cmd_max 0xce + +.align 4 +crypt_dtable: +.b16 #crypt_copy_prep #crypt_do_inout +.b16 #crypt_store_prep #crypt_do_out +.b16 #crypt_ecb_e_prep #crypt_do_inout +.b16 #crypt_ecb_d_prep #crypt_do_inout +.b16 #crypt_cbc_e_prep #crypt_do_inout +.b16 #crypt_cbc_d_prep #crypt_do_inout +.b16 #crypt_pcbc_e_prep #crypt_do_inout +.b16 #crypt_pcbc_d_prep #crypt_do_inout +.b16 #crypt_cfb_e_prep #crypt_do_inout +.b16 #crypt_cfb_d_prep #crypt_do_inout +.b16 #crypt_ofb_prep #crypt_do_inout +.b16 #crypt_ctr_prep #crypt_do_inout +.b16 #crypt_cbc_mac_prep #crypt_do_in +.b16 #crypt_cmac_finish_complete_prep #crypt_do_in +.b16 #crypt_cmac_finish_partial_prep #crypt_do_in + +.align 0x100 + +.section #nv98_pcrypt_code + + // $r0 is always set to 0 in our code - this allows some space savings. + clear b32 $r0 + + // set up the interrupt handler + mov $r1 #ih + mov $iv0 $r1 + + // init stack pointer + mov $sp $r0 + + // set interrupt dispatch - route timer, fifo, ctxswitch to i0, others to host + movw $r1 0xfff0 + sethi $r1 0 + mov $r2 0x400 + iowr I[$r2 + 0x300] $r1 + + // enable the interrupts + or $r1 0xc + iowr I[$r2] $r1 + + // enable fifo access and context switching + mov $r1 3 + mov $r2 0x1200 + iowr I[$r2] $r1 + + // enable i0 delivery + bset $flags ie0 + + // sleep forver, waking only for interrupts. + bset $flags $p0 + spin: + sleep $p0 + bra #spin + +// i0 handler +ih: + // see which interrupts we got + iord $r1 I[$r0 + 0x200] + + and $r2 $r1 0x8 + cmpu b32 $r2 0 + bra e #noctx + + // context switch... prepare the regs for xfer + mov $r2 0x7700 + mov $xtargets $r2 + mov $xdbase $r0 + // 128-byte context. + mov $r2 0 + sethi $r2 0x50000 + + // read current channel + mov $r3 0x1400 + iord $r4 I[$r3] + // if bit 30 set, it's active, so we have to unload it first. + shl b32 $r5 $r4 1 + cmps b32 $r5 0 + bra nc #ctxload + + // unload the current channel - save the context + xdst $r0 $r2 + xdwait + // and clear bit 30, then write back + bclr $r4 0x1e + iowr I[$r3] $r4 + // tell PFIFO we unloaded + mov $r4 1 + iowr I[$r3 + 0x200] $r4 + + bra #noctx + + ctxload: + // no channel loaded - perhaps we're requested to load one + iord $r4 I[$r3 + 0x100] + shl b32 $r15 $r4 1 + cmps b32 $r15 0 + // if bit 30 of next channel not set, probably PFIFO is just + // killing a context. do a faux load, without the active bit. + bra nc #dummyload + + // ok, do a real context load. + xdld $r0 $r2 + xdwait + mov $r5 #ctx_dma + mov $r6 #dma_count - 1 + ctxload_dma_loop: + ld b32 $r7 D[$r5 + $r6 * 4] + add b32 $r8 $r6 0x180 + shl b32 $r8 8 + iowr I[$r8] $r7 + sub b32 $r6 1 + bra nc #ctxload_dma_loop + + dummyload: + // tell PFIFO we're done + mov $r5 2 + iowr I[$r3 + 0x200] $r5 + + noctx: + and $r2 $r1 0x4 + cmpu b32 $r2 0 + bra e #nocmd + + // incoming fifo command. + mov $r3 0x1900 + iord $r2 I[$r3 + 0x100] + iord $r3 I[$r3] + // extract the method + and $r4 $r2 0x7ff + // shift the addr to proper position if we need to interrupt later + shl b32 $r2 0x10 + + // mthd 0 and 0x100 [NAME, NOP]: ignore + and $r5 $r4 0x7bf + cmpu b32 $r5 0 + bra e #cmddone + + mov $r5 #engine_cmd_dtable - 0xc0 * 8 + mov $r6 #engine_cmd_max + cmpu b32 $r4 0xc0 + bra nc #dtable_cmd + mov $r5 #common_cmd_dtable - 0x80 * 8 + mov $r6 #common_cmd_max + cmpu b32 $r4 0x80 + bra nc #dtable_cmd + cmpu b32 $r4 0x60 + bra nc #dma_cmd + cmpu b32 $r4 0x50 + bra ne #illegal_mthd + + // mthd 0x140: PM_TRIGGER + mov $r2 0x2200 + clear b32 $r3 + sethi $r3 0x20000 + iowr I[$r2] $r3 + bra #cmddone + + dma_cmd: + // mthd 0x180...: DMA_* + cmpu b32 $r4 0x60+#dma_count + bra nc #illegal_mthd + shl b32 $r5 $r4 2 + add b32 $r5 (#ctx_dma - 0x60 * 4) & 0xffff + st b32 D[$r5] $r3 + add b32 $r4 0x180 - 0x60 + shl b32 $r4 8 + bset $r3 0x1e + iowr I[$r4] $r3 + bra #cmddone + + dtable_cmd: + cmpu b32 $r4 $r6 + bra nc #illegal_mthd + shl b32 $r4 3 + add b32 $r4 $r5 + ld b32 $r5 D[$r4 + 4] + and $r5 $r3 + cmpu b32 $r5 0 + bra ne #invalid_bitfield + ld b16 $r5 D[$r4] + ld b16 $r6 D[$r4 + 2] + cmpu b32 $r6 2 + bra e #cmd_setctx + ld b32 $r7 D[$r0 + #ctx_cond_off] + and $r6 $r7 + cmpu b32 $r6 1 + bra e #cmddone + call $r5 + bra $p1 #dispatch_error + bra #cmddone + + cmd_setctx: + st b32 D[$r5] $r3 + bra #cmddone + + + invalid_bitfield: + or $r2 1 + dispatch_error: + illegal_mthd: + mov $r4 0x1000 + iowr I[$r4] $r2 + iowr I[$r4 + 0x100] $r3 + mov $r4 0x40 + iowr I[$r0] $r4 + + im_loop: + iord $r4 I[$r0 + 0x200] + and $r4 0x40 + cmpu b32 $r4 0 + bra ne #im_loop + + cmddone: + // remove the command from FIFO + mov $r3 0x1d00 + mov $r4 1 + iowr I[$r3] $r4 + + nocmd: + // ack the processed interrupts + and $r1 $r1 0xc + iowr I[$r0 + 0x100] $r1 +iret + +cmd_query_get: + // if bit 0 of param set, trigger interrupt afterwards. + setp $p1 $r3 + or $r2 3 + + // read PTIMER, beware of races... + mov $r4 0xb00 + ptimer_retry: + iord $r6 I[$r4 + 0x100] + iord $r5 I[$r4] + iord $r7 I[$r4 + 0x100] + cmpu b32 $r6 $r7 + bra ne #ptimer_retry + + // prepare the query structure + ld b32 $r4 D[$r0 + #ctx_query_counter] + st b32 D[$r0 + #swap + 0x0] $r4 + st b32 D[$r0 + #swap + 0x4] $r0 + st b32 D[$r0 + #swap + 0x8] $r5 + st b32 D[$r0 + #swap + 0xc] $r6 + + // will use target 0, DMA_QUERY. + mov $xtargets $r0 + + ld b32 $r4 D[$r0 + #ctx_query_address_high] + shl b32 $r4 0x18 + mov $xdbase $r4 + + ld b32 $r4 D[$r0 + #ctx_query_address_low] + mov $r5 #swap + sethi $r5 0x20000 + xdst $r4 $r5 + xdwait + + ret + +cmd_cond_mode: + // if >= 5, INVALID_ENUM + bset $flags $p1 + or $r2 2 + cmpu b32 $r3 5 + bra nc #return + + // otherwise, no error. + bclr $flags $p1 + + // if < 2, no QUERY object is involved + cmpu b32 $r3 2 + bra nc #cmd_cond_mode_queryful + + xor $r3 1 + st b32 D[$r0 + #ctx_cond_off] $r3 + return: + ret + + cmd_cond_mode_queryful: + // ok, will need to pull a QUERY object, prepare offsets + ld b32 $r4 D[$r0 + #ctx_cond_address_high] + ld b32 $r5 D[$r0 + #ctx_cond_address_low] + and $r6 $r5 0xff + shr b32 $r5 8 + shl b32 $r4 0x18 + or $r4 $r5 + mov $xdbase $r4 + mov $xtargets $r0 + + // pull the first one + mov $r5 #swap + sethi $r5 0x20000 + xdld $r6 $r5 + + // if == 2, only a single QUERY is involved... + cmpu b32 $r3 2 + bra ne #cmd_cond_mode_double + + xdwait + ld b32 $r4 D[$r0 + #swap + 4] + cmpu b32 $r4 0 + xbit $r4 $flags z + st b32 D[$r0 + #ctx_cond_off] $r4 + ret + + // ok, we'll need to pull second one too + cmd_cond_mode_double: + add b32 $r6 0x10 + add b32 $r5 0x10 + xdld $r6 $r5 + xdwait + + // compare COUNTERs + ld b32 $r5 D[$r0 + #swap + 0x00] + ld b32 $r6 D[$r0 + #swap + 0x10] + cmpu b32 $r5 $r6 + xbit $r4 $flags z + + // compare RESen + ld b32 $r5 D[$r0 + #swap + 0x04] + ld b32 $r6 D[$r0 + #swap + 0x14] + cmpu b32 $r5 $r6 + xbit $r5 $flags z + and $r4 $r5 + + // and negate or not, depending on mode + cmpu b32 $r3 3 + xbit $r5 $flags z + xor $r4 $r5 + st b32 D[$r0 + #ctx_cond_off] $r4 + ret + +cmd_wrcache_flush: + bclr $flags $p1 + mov $r2 0x2200 + clear b32 $r3 + sethi $r3 0x10000 + iowr I[$r2] $r3 + ret + +crypt_cmd_mode: + // if >= 0xf, INVALID_ENUM + bset $flags $p1 + or $r2 2 + cmpu b32 $r3 0xf + bra nc #crypt_cmd_mode_return + + bclr $flags $p1 + st b32 D[$r0 + #ctx_mode] $r3 + + crypt_cmd_mode_return: + ret + +crypt_cmd_length: + // nop if length == 0 + cmpu b32 $r3 0 + bra e #crypt_cmd_mode_return + + // init key, IV + cxset 3 + mov $r4 #ctx_key + sethi $r4 0x70000 + xdst $r0 $r4 + mov $r4 #ctx_iv + sethi $r4 0x60000 + xdst $r0 $r4 + xdwait + ckeyreg $c7 + + // prepare the targets + mov $r4 0x2100 + mov $xtargets $r4 + + // prepare src address + ld b32 $r4 D[$r0 + #ctx_src_address_high] + ld b32 $r5 D[$r0 + #ctx_src_address_low] + shr b32 $r8 $r5 8 + shl b32 $r4 0x18 + or $r4 $r8 + and $r5 $r5 0xff + + // prepare dst address + ld b32 $r6 D[$r0 + #ctx_dst_address_high] + ld b32 $r7 D[$r0 + #ctx_dst_address_low] + shr b32 $r8 $r7 8 + shl b32 $r6 0x18 + or $r6 $r8 + and $r7 $r7 0xff + + // find the proper prep & do functions + ld b32 $r8 D[$r0 + #ctx_mode] + shl b32 $r8 2 + + // run prep + ld b16 $r9 D[$r8 + #crypt_dtable] + call $r9 + + // do it + ld b16 $r9 D[$r8 + #crypt_dtable + 2] + call $r9 + cxset 1 + xdwait + cxset 0x61 + xdwait + xdwait + + // update src address + shr b32 $r8 $r4 0x18 + shl b32 $r9 $r4 8 + add b32 $r9 $r5 + adc b32 $r8 0 + st b32 D[$r0 + #ctx_src_address_high] $r8 + st b32 D[$r0 + #ctx_src_address_low] $r9 + + // update dst address + shr b32 $r8 $r6 0x18 + shl b32 $r9 $r6 8 + add b32 $r9 $r7 + adc b32 $r8 0 + st b32 D[$r0 + #ctx_dst_address_high] $r8 + st b32 D[$r0 + #ctx_dst_address_low] $r9 + + // pull updated IV + cxset 2 + mov $r4 #ctx_iv + sethi $r4 0x60000 + xdld $r0 $r4 + xdwait + + ret + + +crypt_copy_prep: + cs0begin 2 + cxsin $c0 + cxsout $c0 + ret + +crypt_store_prep: + cs0begin 1 + cxsout $c6 + ret + +crypt_ecb_e_prep: + cs0begin 3 + cxsin $c0 + cenc $c0 $c0 + cxsout $c0 + ret + +crypt_ecb_d_prep: + ckexp $c7 $c7 + cs0begin 3 + cxsin $c0 + cdec $c0 $c0 + cxsout $c0 + ret + +crypt_cbc_e_prep: + cs0begin 4 + cxsin $c0 + cxor $c6 $c0 + cenc $c6 $c6 + cxsout $c6 + ret + +crypt_cbc_d_prep: + ckexp $c7 $c7 + cs0begin 5 + cmov $c2 $c6 + cxsin $c6 + cdec $c0 $c6 + cxor $c0 $c2 + cxsout $c0 + ret + +crypt_pcbc_e_prep: + cs0begin 5 + cxsin $c0 + cxor $c6 $c0 + cenc $c6 $c6 + cxsout $c6 + cxor $c6 $c0 + ret + +crypt_pcbc_d_prep: + ckexp $c7 $c7 + cs0begin 5 + cxsin $c0 + cdec $c1 $c0 + cxor $c6 $c1 + cxsout $c6 + cxor $c6 $c0 + ret + +crypt_cfb_e_prep: + cs0begin 4 + cenc $c6 $c6 + cxsin $c0 + cxor $c6 $c0 + cxsout $c6 + ret + +crypt_cfb_d_prep: + cs0begin 4 + cenc $c0 $c6 + cxsin $c6 + cxor $c0 $c6 + cxsout $c0 + ret + +crypt_ofb_prep: + cs0begin 4 + cenc $c6 $c6 + cxsin $c0 + cxor $c0 $c6 + cxsout $c0 + ret + +crypt_ctr_prep: + cs0begin 5 + cenc $c1 $c6 + cadd $c6 1 + cxsin $c0 + cxor $c0 $c1 + cxsout $c0 + ret + +crypt_cbc_mac_prep: + cs0begin 3 + cxsin $c0 + cxor $c6 $c0 + cenc $c6 $c6 + ret + +crypt_cmac_finish_complete_prep: + cs0begin 7 + cxsin $c0 + cxor $c6 $c0 + cxor $c0 $c0 + cenc $c0 $c0 + cprecmac $c0 $c0 + cxor $c6 $c0 + cenc $c6 $c6 + ret + +crypt_cmac_finish_partial_prep: + cs0begin 8 + cxsin $c0 + cxor $c6 $c0 + cxor $c0 $c0 + cenc $c0 $c0 + cprecmac $c0 $c0 + cprecmac $c0 $c0 + cxor $c6 $c0 + cenc $c6 $c6 + ret + +// TODO +crypt_do_in: + add b32 $r3 $r5 + mov $xdbase $r4 + mov $r9 #swap + sethi $r9 0x20000 + crypt_do_in_loop: + xdld $r5 $r9 + xdwait + cxset 0x22 + xdst $r0 $r9 + cs0exec 1 + xdwait + add b32 $r5 0x10 + cmpu b32 $r5 $r3 + bra ne #crypt_do_in_loop + cxset 1 + xdwait + ret + +crypt_do_out: + add b32 $r3 $r7 + mov $xdbase $r6 + mov $r9 #swap + sethi $r9 0x20000 + crypt_do_out_loop: + cs0exec 1 + cxset 0x61 + xdld $r7 $r9 + xdst $r7 $r9 + cxset 1 + xdwait + add b32 $r7 0x10 + cmpu b32 $r7 $r3 + bra ne #crypt_do_out_loop + ret + +crypt_do_inout: + add b32 $r3 $r5 + mov $r9 #swap + sethi $r9 0x20000 + crypt_do_inout_loop: + mov $xdbase $r4 + xdld $r5 $r9 + xdwait + cxset 0x21 + xdst $r0 $r9 + cs0exec 1 + cxset 0x61 + mov $xdbase $r6 + xdld $r7 $r9 + xdst $r7 $r9 + cxset 1 + xdwait + add b32 $r5 0x10 + add b32 $r7 0x10 + cmpu b32 $r5 $r3 + bra ne #crypt_do_inout_loop + ret + +.align 0x100 + diff --git a/driver/pscnv/nva3_copy.fuc b/driver/pscnv/nva3_copy.fuc new file mode 100644 index 00000000..abc36626 --- /dev/null +++ b/driver/pscnv/nva3_copy.fuc @@ -0,0 +1,872 @@ +/* fuc microcode for copy engine on nva3- chipsets + * + * Copyright 2011 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +/* To build for nva3:nvc0 + * m4 -DNVA3 nva3_copy.fuc | envyas -a -w -m fuc -V nva3 -o nva3_copy.fuc.h + * + * To build for nvc0- + * m4 -DNVC0 nva3_copy.fuc | envyas -a -w -m fuc -V nva3 -o nvc0_copy.fuc.h + */ + +ifdef(`NVA3', +.section #nva3_pcopy_data +, +.section #nvc0_pcopy_data +) + +ctx_object: .b32 0 +ifdef(`NVA3', +ctx_dma: +ctx_dma_query: .b32 0 +ctx_dma_src: .b32 0 +ctx_dma_dst: .b32 0 +,) +.equ #ctx_dma_count 3 +ctx_query_address_high: .b32 0 +ctx_query_address_low: .b32 0 +ctx_query_counter: .b32 0 +ctx_src_address_high: .b32 0 +ctx_src_address_low: .b32 0 +ctx_src_pitch: .b32 0 +ctx_src_tile_mode: .b32 0 +ctx_src_xsize: .b32 0 +ctx_src_ysize: .b32 0 +ctx_src_zsize: .b32 0 +ctx_src_zoff: .b32 0 +ctx_src_xoff: .b32 0 +ctx_src_yoff: .b32 0 +ctx_src_cpp: .b32 0 +ctx_dst_address_high: .b32 0 +ctx_dst_address_low: .b32 0 +ctx_dst_pitch: .b32 0 +ctx_dst_tile_mode: .b32 0 +ctx_dst_xsize: .b32 0 +ctx_dst_ysize: .b32 0 +ctx_dst_zsize: .b32 0 +ctx_dst_zoff: .b32 0 +ctx_dst_xoff: .b32 0 +ctx_dst_yoff: .b32 0 +ctx_dst_cpp: .b32 0 +ctx_format: .b32 0 +ctx_swz_const0: .b32 0 +ctx_swz_const1: .b32 0 +ctx_xcnt: .b32 0 +ctx_ycnt: .b32 0 +.align 256 + +dispatch_table: +// mthd 0x0000, NAME +.b16 0x000 1 +.b32 #ctx_object ~0xffffffff +// mthd 0x0100, NOP +.b16 0x040 1 +.b32 0x00010000 + #cmd_nop ~0xffffffff +// mthd 0x0140, PM_TRIGGER +.b16 0x050 1 +.b32 0x00010000 + #cmd_pm_trigger ~0xffffffff +ifdef(`NVA3', ` +// mthd 0x0180-0x018c, DMA_ +.b16 0x060 #ctx_dma_count +dispatch_dma: +.b32 0x00010000 + #cmd_dma ~0xffffffff +.b32 0x00010000 + #cmd_dma ~0xffffffff +.b32 0x00010000 + #cmd_dma ~0xffffffff +',) +// mthd 0x0200-0x0218, SRC_TILE +.b16 0x80 7 +.b32 #ctx_src_tile_mode ~0x00000fff +.b32 #ctx_src_xsize ~0x0007ffff +.b32 #ctx_src_ysize ~0x00001fff +.b32 #ctx_src_zsize ~0x000007ff +.b32 #ctx_src_zoff ~0x00000fff +.b32 #ctx_src_xoff ~0x0007ffff +.b32 #ctx_src_yoff ~0x00001fff +// mthd 0x0220-0x0238, DST_TILE +.b16 0x88 7 +.b32 #ctx_dst_tile_mode ~0x00000fff +.b32 #ctx_dst_xsize ~0x0007ffff +.b32 #ctx_dst_ysize ~0x00001fff +.b32 #ctx_dst_zsize ~0x000007ff +.b32 #ctx_dst_zoff ~0x00000fff +.b32 #ctx_dst_xoff ~0x0007ffff +.b32 #ctx_dst_yoff ~0x00001fff +// mthd 0x0300-0x0304, EXEC, WRCACHE_FLUSH +.b16 0xc0 2 +.b32 0x00010000 + #cmd_exec ~0xffffffff +.b32 0x00010000 + #cmd_wrcache_flush ~0xffffffff +// mthd 0x030c-0x0340, various stuff +.b16 0xc3 14 +.b32 #ctx_src_address_high ~0x000000ff +.b32 #ctx_src_address_low ~0xfffffff0 +.b32 #ctx_dst_address_high ~0x000000ff +.b32 #ctx_dst_address_low ~0xfffffff0 +.b32 #ctx_src_pitch ~0x0007ffff +.b32 #ctx_dst_pitch ~0x0007ffff +.b32 #ctx_xcnt ~0x0000ffff +.b32 #ctx_ycnt ~0x00001fff +.b32 #ctx_format ~0x0333ffff +.b32 #ctx_swz_const0 ~0xffffffff +.b32 #ctx_swz_const1 ~0xffffffff +.b32 #ctx_query_address_high ~0x000000ff +.b32 #ctx_query_address_low ~0xffffffff +.b32 #ctx_query_counter ~0xffffffff +.b16 0x800 0 + +ifdef(`NVA3', +.section #nva3_pcopy_code +, +.section #nvc0_pcopy_code +) + +main: + clear b32 $r0 + mov $sp $r0 + + // setup i0 handler and route fifo and ctxswitch to it + mov $r1 #ih + mov $iv0 $r1 + mov $r1 0x400 + movw $r2 0xfff3 + sethi $r2 0 + iowr I[$r1 + 0x300] $r2 + + // enable interrupts + or $r2 0xc + iowr I[$r1] $r2 + bset $flags ie0 + + // enable fifo access and context switching + mov $r1 0x1200 + mov $r2 3 + iowr I[$r1] $r2 + + // sleep forever, waking for interrupts + bset $flags $p0 + spin: + sleep $p0 + bra #spin + +// i0 handler +ih: + iord $r1 I[$r0 + 0x200] + + and $r2 $r1 0x00000008 + bra e #ih_no_chsw + call #chsw + ih_no_chsw: + and $r2 $r1 0x00000004 + bra e #ih_no_cmd + call #dispatch + + ih_no_cmd: + and $r1 $r1 0x0000000c + iowr I[$r0 + 0x100] $r1 + iret + +// $p1 direction (0 = unload, 1 = load) +// $r3 channel +swctx: + mov $r4 0x7700 + mov $xtargets $r4 +ifdef(`NVA3', ` + // target 7 hardcoded to ctx dma object + mov $xdbase $r0 +', ` // NVC0 + // read SCRATCH3 to decide if we are PCOPY0 or PCOPY1 + mov $r4 0x2100 + iord $r4 I[$r4 + 0] + and $r4 1 + shl b32 $r4 4 + add b32 $r4 0x30 + + // channel is in vram + mov $r15 0x61c + shl b32 $r15 6 + mov $r5 0x114 + iowrs I[$r15] $r5 + + // read 16-byte PCOPYn info, containing context pointer, from channel + shl b32 $r5 $r3 4 + add b32 $r5 2 + mov $xdbase $r5 + mov $r5 $sp + // get a chunk of stack space, aligned to 256 byte boundary + sub b32 $r5 0x100 + mov $r6 0xff + not b32 $r6 + and $r5 $r6 + sethi $r5 0x00020000 + xdld $r4 $r5 + xdwait + sethi $r5 0 + + // set context pointer, from within channel VM + mov $r14 0 + iowrs I[$r15] $r14 + ld b32 $r4 D[$r5 + 0] + shr b32 $r4 8 + ld b32 $r6 D[$r5 + 4] + shl b32 $r6 24 + or $r4 $r6 + mov $xdbase $r4 +') + // 256-byte context, at start of data segment + mov b32 $r4 $r0 + sethi $r4 0x60000 + + // swap! + bra $p1 #swctx_load + xdst $r0 $r4 + bra #swctx_done + swctx_load: + xdld $r0 $r4 + swctx_done: + xdwait + ret + +chsw: + // read current channel + mov $r2 0x1400 + iord $r3 I[$r2] + + // if it's active, unload it and return + xbit $r15 $r3 0x1e + bra e #chsw_no_unload + bclr $flags $p1 + call #swctx + bclr $r3 0x1e + iowr I[$r2] $r3 + mov $r4 1 + iowr I[$r2 + 0x200] $r4 + ret + + // read next channel + chsw_no_unload: + iord $r3 I[$r2 + 0x100] + + // is there a channel waiting to be loaded? + xbit $r13 $r3 0x1e + bra e #chsw_finish_load + bset $flags $p1 + call #swctx +ifdef(`NVA3', + // load dma objects back into TARGET regs + mov $r5 #ctx_dma + mov $r6 #ctx_dma_count + chsw_load_ctx_dma: + ld b32 $r7 D[$r5 + $r6 * 4] + add b32 $r8 $r6 0x180 + shl b32 $r8 8 + iowr I[$r8] $r7 + sub b32 $r6 1 + bra nc #chsw_load_ctx_dma +,) + + chsw_finish_load: + mov $r3 2 + iowr I[$r2 + 0x200] $r3 + ret + +dispatch: + // read incoming fifo command + mov $r3 0x1900 + iord $r2 I[$r3 + 0x100] + iord $r3 I[$r3 + 0x000] + and $r4 $r2 0x7ff + // $r2 will be used to store exception data + shl b32 $r2 0x10 + + // lookup method in the dispatch table, ILLEGAL_MTHD if not found + mov $r5 #dispatch_table + clear b32 $r6 + clear b32 $r7 + dispatch_loop: + ld b16 $r6 D[$r5 + 0] + ld b16 $r7 D[$r5 + 2] + add b32 $r5 4 + cmpu b32 $r4 $r6 + bra c #dispatch_illegal_mthd + add b32 $r7 $r6 + cmpu b32 $r4 $r7 + bra c #dispatch_valid_mthd + sub b32 $r7 $r6 + shl b32 $r7 3 + add b32 $r5 $r7 + bra #dispatch_loop + + // ensure no bits set in reserved fields, INVALID_BITFIELD + dispatch_valid_mthd: + sub b32 $r4 $r6 + shl b32 $r4 3 + add b32 $r4 $r5 + ld b32 $r5 D[$r4 + 4] + and $r5 $r3 + cmpu b32 $r5 0 + bra ne #dispatch_invalid_bitfield + + // depending on dispatch flags: execute method, or save data as state + ld b16 $r5 D[$r4 + 0] + ld b16 $r6 D[$r4 + 2] + cmpu b32 $r6 0 + bra ne #dispatch_cmd + st b32 D[$r5] $r3 + bra #dispatch_done + dispatch_cmd: + bclr $flags $p1 + call $r5 + bra $p1 #dispatch_error + bra #dispatch_done + + dispatch_invalid_bitfield: + or $r2 2 + dispatch_illegal_mthd: + or $r2 1 + + // store exception data in SCRATCH0/SCRATCH1, signal hostirq + dispatch_error: + mov $r4 0x1000 + iowr I[$r4 + 0x000] $r2 + iowr I[$r4 + 0x100] $r3 + mov $r2 0x40 + iowr I[$r0] $r2 + hostirq_wait: + iord $r2 I[$r0 + 0x200] + and $r2 0x40 + cmpu b32 $r2 0 + bra ne #hostirq_wait + + dispatch_done: + mov $r2 0x1d00 + mov $r3 1 + iowr I[$r2] $r3 + ret + +// No-operation +// +// Inputs: +// $r1: irqh state +// $r2: hostirq state +// $r3: data +// $r4: dispatch table entry +// Outputs: +// $r1: irqh state +// $p1: set on error +// $r2: hostirq state +// $r3: data +cmd_nop: + ret + +// PM_TRIGGER +// +// Inputs: +// $r1: irqh state +// $r2: hostirq state +// $r3: data +// $r4: dispatch table entry +// Outputs: +// $r1: irqh state +// $p1: set on error +// $r2: hostirq state +// $r3: data +cmd_pm_trigger: + mov $r2 0x2200 + clear b32 $r3 + sethi $r3 0x20000 + iowr I[$r2] $r3 + ret + +ifdef(`NVA3', +// SET_DMA_* method handler +// +// Inputs: +// $r1: irqh state +// $r2: hostirq state +// $r3: data +// $r4: dispatch table entry +// Outputs: +// $r1: irqh state +// $p1: set on error +// $r2: hostirq state +// $r3: data +cmd_dma: + sub b32 $r4 #dispatch_dma + shr b32 $r4 1 + bset $r3 0x1e + st b32 D[$r4 + #ctx_dma] $r3 + add b32 $r4 0x600 + shl b32 $r4 6 + iowr I[$r4] $r3 + ret +,) + +// Calculates the hw swizzle mask and adjusts the surface's xcnt to match +// +cmd_exec_set_format: + // zero out a chunk of the stack to store the swizzle into + add $sp -0x10 + st b32 D[$sp + 0x00] $r0 + st b32 D[$sp + 0x04] $r0 + st b32 D[$sp + 0x08] $r0 + st b32 D[$sp + 0x0c] $r0 + + // extract cpp, src_ncomp and dst_ncomp from FORMAT + ld b32 $r4 D[$r0 + #ctx_format] + extr $r5 $r4 16:17 + add b32 $r5 1 + extr $r6 $r4 20:21 + add b32 $r6 1 + extr $r7 $r4 24:25 + add b32 $r7 1 + + // convert FORMAT swizzle mask to hw swizzle mask + bclr $flags $p2 + clear b32 $r8 + clear b32 $r9 + ncomp_loop: + and $r10 $r4 0xf + shr b32 $r4 4 + clear b32 $r11 + bpc_loop: + cmpu b8 $r10 4 + bra nc #cmp_c0 + mulu $r12 $r10 $r5 + add b32 $r12 $r11 + bset $flags $p2 + bra #bpc_next + cmp_c0: + bra ne #cmp_c1 + mov $r12 0x10 + add b32 $r12 $r11 + bra #bpc_next + cmp_c1: + cmpu b8 $r10 6 + bra nc #cmp_zero + mov $r12 0x14 + add b32 $r12 $r11 + bra #bpc_next + cmp_zero: + mov $r12 0x80 + bpc_next: + st b8 D[$sp + $r8] $r12 + add b32 $r8 1 + add b32 $r11 1 + cmpu b32 $r11 $r5 + bra c #bpc_loop + add b32 $r9 1 + cmpu b32 $r9 $r7 + bra c #ncomp_loop + + // SRC_XCNT = (xcnt * src_cpp), or 0 if no src ref in swz (hw will hang) + mulu $r6 $r5 + st b32 D[$r0 + #ctx_src_cpp] $r6 + ld b32 $r8 D[$r0 + #ctx_xcnt] + mulu $r6 $r8 + bra $p2 #dst_xcnt + clear b32 $r6 + + dst_xcnt: + mulu $r7 $r5 + st b32 D[$r0 + #ctx_dst_cpp] $r7 + mulu $r7 $r8 + + mov $r5 0x810 + shl b32 $r5 6 + iowr I[$r5 + 0x000] $r6 + iowr I[$r5 + 0x100] $r7 + add b32 $r5 0x800 + ld b32 $r6 D[$r0 + #ctx_dst_cpp] + sub b32 $r6 1 + shl b32 $r6 8 + ld b32 $r7 D[$r0 + #ctx_src_cpp] + sub b32 $r7 1 + or $r6 $r7 + iowr I[$r5 + 0x000] $r6 + add b32 $r5 0x100 + ld b32 $r6 D[$sp + 0x00] + iowr I[$r5 + 0x000] $r6 + ld b32 $r6 D[$sp + 0x04] + iowr I[$r5 + 0x100] $r6 + ld b32 $r6 D[$sp + 0x08] + iowr I[$r5 + 0x200] $r6 + ld b32 $r6 D[$sp + 0x0c] + iowr I[$r5 + 0x300] $r6 + add b32 $r5 0x400 + ld b32 $r6 D[$r0 + #ctx_swz_const0] + iowr I[$r5 + 0x000] $r6 + ld b32 $r6 D[$r0 + #ctx_swz_const1] + iowr I[$r5 + 0x100] $r6 + add $sp 0x10 + ret + +// Setup to handle a tiled surface +// +// Calculates a number of parameters the hardware requires in order +// to correctly handle tiling. +// +// Offset calculation is performed as follows (Tp/Th/Td from TILE_MODE): +// nTx = round_up(w * cpp, 1 << Tp) >> Tp +// nTy = round_up(h, 1 << Th) >> Th +// Txo = (x * cpp) & ((1 << Tp) - 1) +// Tx = (x * cpp) >> Tp +// Tyo = y & ((1 << Th) - 1) +// Ty = y >> Th +// Tzo = z & ((1 << Td) - 1) +// Tz = z >> Td +// +// off = (Tzo << Tp << Th) + (Tyo << Tp) + Txo +// off += ((Tz * nTy * nTx)) + (Ty * nTx) + Tx) << Td << Th << Tp; +// +// Inputs: +// $r4: hw command (0x104800) +// $r5: ctx offset adjustment for src/dst selection +// $p2: set if dst surface +// +cmd_exec_set_surface_tiled: + // translate TILE_MODE into Tp, Th, Td shift values + ld b32 $r7 D[$r5 + #ctx_src_tile_mode] + extr $r9 $r7 8:11 + extr $r8 $r7 4:7 +ifdef(`NVA3', + add b32 $r8 2 +, + add b32 $r8 3 +) + extr $r7 $r7 0:3 + cmp b32 $r7 0xe + bra ne #xtile64 + mov $r7 4 + bra #xtileok + xtile64: + xbit $r7 $flags $p2 + add b32 $r7 17 + bset $r4 $r7 + mov $r7 6 + xtileok: + + // Op = (x * cpp) & ((1 << Tp) - 1) + // Tx = (x * cpp) >> Tp + ld b32 $r10 D[$r5 + #ctx_src_xoff] + ld b32 $r11 D[$r5 + #ctx_src_cpp] + mulu $r10 $r11 + mov $r11 1 + shl b32 $r11 $r7 + sub b32 $r11 1 + and $r12 $r10 $r11 + shr b32 $r10 $r7 + + // Tyo = y & ((1 << Th) - 1) + // Ty = y >> Th + ld b32 $r13 D[$r5 + #ctx_src_yoff] + mov $r14 1 + shl b32 $r14 $r8 + sub b32 $r14 1 + and $r11 $r13 $r14 + shr b32 $r13 $r8 + + // YTILE = ((1 << Th) << 12) | ((1 << Th) - Tyo) + add b32 $r14 1 + shl b32 $r15 $r14 12 + sub b32 $r14 $r11 + or $r15 $r14 + xbit $r6 $flags $p2 + add b32 $r6 0x208 + shl b32 $r6 8 + iowr I[$r6 + 0x000] $r15 + + // Op += Tyo << Tp + shl b32 $r11 $r7 + add b32 $r12 $r11 + + // nTx = ((w * cpp) + ((1 << Tp) - 1) >> Tp) + ld b32 $r15 D[$r5 + #ctx_src_xsize] + ld b32 $r11 D[$r5 + #ctx_src_cpp] + mulu $r15 $r11 + mov $r11 1 + shl b32 $r11 $r7 + sub b32 $r11 1 + add b32 $r15 $r11 + shr b32 $r15 $r7 + push $r15 + + // nTy = (h + ((1 << Th) - 1)) >> Th + ld b32 $r15 D[$r5 + #ctx_src_ysize] + mov $r11 1 + shl b32 $r11 $r8 + sub b32 $r11 1 + add b32 $r15 $r11 + shr b32 $r15 $r8 + push $r15 + + // Tys = Tp + Th + // CFG_YZ_TILE_SIZE = ((1 << Th) >> 2) << Td + add b32 $r7 $r8 + sub b32 $r8 2 + mov $r11 1 + shl b32 $r11 $r8 + shl b32 $r11 $r9 + + // Tzo = z & ((1 << Td) - 1) + // Tz = z >> Td + // Op += Tzo << Tys + // Ts = Tys + Td + ld b32 $r8 D[$r5 + #ctx_src_zoff] + mov $r14 1 + shl b32 $r14 $r9 + sub b32 $r14 1 + and $r15 $r8 $r14 + shl b32 $r15 $r7 + add b32 $r12 $r15 + add b32 $r7 $r9 + shr b32 $r8 $r9 + + // Ot = ((Tz * nTy * nTx) + (Ty * nTx) + Tx) << Ts + pop $r15 + pop $r9 + mulu $r13 $r9 + add b32 $r10 $r13 + mulu $r8 $r9 + mulu $r8 $r15 + add b32 $r10 $r8 + shl b32 $r10 $r7 + + // PITCH = (nTx - 1) << Ts + sub b32 $r9 1 + shl b32 $r9 $r7 + iowr I[$r6 + 0x200] $r9 + + // SRC_ADDRESS_LOW = (Ot + Op) & 0xffffffff + // CFG_ADDRESS_HIGH |= ((Ot + Op) >> 32) << 16 + ld b32 $r7 D[$r5 + #ctx_src_address_low] + ld b32 $r8 D[$r5 + #ctx_src_address_high] + add b32 $r10 $r12 + add b32 $r7 $r10 + adc b32 $r8 0 + shl b32 $r8 16 + or $r8 $r11 + sub b32 $r6 0x600 + iowr I[$r6 + 0x000] $r7 + add b32 $r6 0x400 + iowr I[$r6 + 0x000] $r8 + ret + +// Setup to handle a linear surface +// +// Nothing to see here.. Sets ADDRESS and PITCH, pretty non-exciting +// +cmd_exec_set_surface_linear: + xbit $r6 $flags $p2 + add b32 $r6 0x202 + shl b32 $r6 8 + ld b32 $r7 D[$r5 + #ctx_src_address_low] + iowr I[$r6 + 0x000] $r7 + add b32 $r6 0x400 + ld b32 $r7 D[$r5 + #ctx_src_address_high] + shl b32 $r7 16 + iowr I[$r6 + 0x000] $r7 + add b32 $r6 0x400 + ld b32 $r7 D[$r5 + #ctx_src_pitch] + iowr I[$r6 + 0x000] $r7 + ret + +// wait for regs to be available for use +cmd_exec_wait: + push $r0 + push $r1 + mov $r0 0x800 + shl b32 $r0 6 + loop: + iord $r1 I[$r0] + and $r1 1 + bra ne #loop + pop $r1 + pop $r0 + ret + +cmd_exec_query: + // if QUERY_SHORT not set, write out { -, 0, TIME_LO, TIME_HI } + xbit $r4 $r3 13 + bra ne #query_counter + call #cmd_exec_wait + mov $r4 0x80c + shl b32 $r4 6 + ld b32 $r5 D[$r0 + #ctx_query_address_low] + add b32 $r5 4 + iowr I[$r4 + 0x000] $r5 + iowr I[$r4 + 0x100] $r0 + mov $r5 0xc + iowr I[$r4 + 0x200] $r5 + add b32 $r4 0x400 + ld b32 $r5 D[$r0 + #ctx_query_address_high] + shl b32 $r5 16 + iowr I[$r4 + 0x000] $r5 + add b32 $r4 0x500 + mov $r5 0x00000b00 + sethi $r5 0x00010000 + iowr I[$r4 + 0x000] $r5 + mov $r5 0x00004040 + shl b32 $r5 1 + sethi $r5 0x80800000 + iowr I[$r4 + 0x100] $r5 + mov $r5 0x00001110 + sethi $r5 0x13120000 + iowr I[$r4 + 0x200] $r5 + mov $r5 0x00001514 + sethi $r5 0x17160000 + iowr I[$r4 + 0x300] $r5 + mov $r5 0x00002601 + sethi $r5 0x00010000 + mov $r4 0x800 + shl b32 $r4 6 + iowr I[$r4 + 0x000] $r5 + + // write COUNTER + query_counter: + call #cmd_exec_wait + mov $r4 0x80c + shl b32 $r4 6 + ld b32 $r5 D[$r0 + #ctx_query_address_low] + iowr I[$r4 + 0x000] $r5 + iowr I[$r4 + 0x100] $r0 + mov $r5 0x4 + iowr I[$r4 + 0x200] $r5 + add b32 $r4 0x400 + ld b32 $r5 D[$r0 + #ctx_query_address_high] + shl b32 $r5 16 + iowr I[$r4 + 0x000] $r5 + add b32 $r4 0x500 + mov $r5 0x00000300 + iowr I[$r4 + 0x000] $r5 + mov $r5 0x00001110 + sethi $r5 0x13120000 + iowr I[$r4 + 0x100] $r5 + ld b32 $r5 D[$r0 + #ctx_query_counter] + add b32 $r4 0x500 + iowr I[$r4 + 0x000] $r5 + mov $r5 0x00002601 + sethi $r5 0x00010000 + mov $r4 0x800 + shl b32 $r4 6 + iowr I[$r4 + 0x000] $r5 + ret + +// Execute a copy operation +// +// Inputs: +// $r1: irqh state +// $r2: hostirq state +// $r3: data +// 000002000 QUERY_SHORT +// 000001000 QUERY +// 000000100 DST_LINEAR +// 000000010 SRC_LINEAR +// 000000001 FORMAT +// $r4: dispatch table entry +// Outputs: +// $r1: irqh state +// $p1: set on error +// $r2: hostirq state +// $r3: data +cmd_exec: + call #cmd_exec_wait + + // if format requested, call function to calculate it, otherwise + // fill in cpp/xcnt for both surfaces as if (cpp == 1) + xbit $r15 $r3 0 + bra e #cmd_exec_no_format + call #cmd_exec_set_format + mov $r4 0x200 + bra #cmd_exec_init_src_surface + cmd_exec_no_format: + mov $r6 0x810 + shl b32 $r6 6 + mov $r7 1 + st b32 D[$r0 + #ctx_src_cpp] $r7 + st b32 D[$r0 + #ctx_dst_cpp] $r7 + ld b32 $r7 D[$r0 + #ctx_xcnt] + iowr I[$r6 + 0x000] $r7 + iowr I[$r6 + 0x100] $r7 + clear b32 $r4 + + cmd_exec_init_src_surface: + bclr $flags $p2 + clear b32 $r5 + xbit $r15 $r3 4 + bra e #src_tiled + call #cmd_exec_set_surface_linear + bra #cmd_exec_init_dst_surface + src_tiled: + call #cmd_exec_set_surface_tiled + bset $r4 7 + + cmd_exec_init_dst_surface: + bset $flags $p2 + mov $r5 #ctx_dst_address_high - #ctx_src_address_high + xbit $r15 $r3 8 + bra e #dst_tiled + call #cmd_exec_set_surface_linear + bra #cmd_exec_kick + dst_tiled: + call #cmd_exec_set_surface_tiled + bset $r4 8 + + cmd_exec_kick: + mov $r5 0x800 + shl b32 $r5 6 + ld b32 $r6 D[$r0 + #ctx_ycnt] + iowr I[$r5 + 0x100] $r6 + mov $r6 0x0041 + // SRC_TARGET = 1, DST_TARGET = 2 + sethi $r6 0x44000000 + or $r4 $r6 + iowr I[$r5] $r4 + + // if requested, queue up a QUERY write after the copy has completed + xbit $r15 $r3 12 + bra e #cmd_exec_done + call #cmd_exec_query + + cmd_exec_done: + ret + +// Flush write cache +// +// Inputs: +// $r1: irqh state +// $r2: hostirq state +// $r3: data +// $r4: dispatch table entry +// Outputs: +// $r1: irqh state +// $p1: set on error +// $r2: hostirq state +// $r3: data +cmd_wrcache_flush: + mov $r2 0x2200 + clear b32 $r3 + sethi $r3 0x10000 + iowr I[$r2] $r3 + ret + +.align 0x100 diff --git a/driver/pscnv/nva3_pm.c b/driver/pscnv/nva3_pm.c new file mode 100644 index 00000000..dbbafed3 --- /dev/null +++ b/driver/pscnv/nva3_pm.c @@ -0,0 +1,95 @@ +/* + * Copyright 2010 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_bios.h" +#include "nouveau_pm.h" + +/*XXX: boards using limits 0x40 need fixing, the register layout + * is correct here, but, there's some other funny magic + * that modifies things, so it's not likely we'll set/read + * the correct timings yet.. working on it... + */ + +struct nva3_pm_state { + struct pll_lims pll; + int N, M, P; +}; + +int +nva3_pm_clock_get(struct drm_device *dev, u32 id) +{ + struct pll_lims pll; + int P, N, M, ret; + u32 reg; + + ret = get_pll_limits(dev, id, &pll); + if (ret) + return ret; + + reg = nv_rd32(dev, pll.reg + 4); + P = (reg & 0x003f0000) >> 16; + N = (reg & 0x0000ff00) >> 8; + M = (reg & 0x000000ff); + return pll.refclk * N / M / P; +} + +void * +nva3_pm_clock_pre(struct drm_device *dev, struct nouveau_pm_level *perflvl, + u32 id, int khz) +{ + struct nva3_pm_state *state; + int dummy, ret; + + state = kzalloc(sizeof(*state), GFP_KERNEL); + if (!state) + return ERR_PTR(-ENOMEM); + + ret = get_pll_limits(dev, id, &state->pll); + if (ret < 0) { + kfree(state); + return (ret == -ENOENT) ? NULL : ERR_PTR(ret); + } + + ret = nv50_calc_pll2(dev, &state->pll, khz, &state->N, &dummy, + &state->M, &state->P); + if (ret < 0) { + kfree(state); + return ERR_PTR(ret); + } + + return state; +} + +void +nva3_pm_clock_set(struct drm_device *dev, void *pre_state) +{ + struct nva3_pm_state *state = pre_state; + u32 reg = state->pll.reg; + + nv_wr32(dev, reg + 4, (state->P << 16) | (state->N << 8) | state->M); + kfree(state); +} + diff --git a/driver/pscnv/nvc0_chan.c b/driver/pscnv/nvc0_chan.c new file mode 100644 index 00000000..fc888f63 --- /dev/null +++ b/driver/pscnv/nvc0_chan.c @@ -0,0 +1,78 @@ +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "nvc0_chan.h" +#include "pscnv_chan.h" +#include "nvc0_vm.h" + +int nvc0_chan_new (struct pscnv_chan *ch) +{ + struct pscnv_vspace *vs = ch->vspace; + struct drm_nouveau_private *dev_priv = ch->dev->dev_private; + unsigned long flags; + + ch->bo = pscnv_mem_alloc(ch->dev, 0x1000, PSCNV_GEM_CONTIG, + 0, (ch->cid < 0 ? 0xc5a2ba7 : 0xc5a2f1f0)); + if (!ch->bo) + return -ENOMEM; + + spin_lock_irqsave(&dev_priv->chan->ch_lock, flags); + ch->handle = ch->bo->start >> 12; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + + if (vs->vid != -3) + dev_priv->vm->map_kernel(ch->bo); + + nv_wv32(ch->bo, 0x200, nvc0_vs(vs)->pd->start); + nv_wv32(ch->bo, 0x204, nvc0_vs(vs)->pd->start >> 32); + nv_wv32(ch->bo, 0x208, vs->size - 1); + nv_wv32(ch->bo, 0x20c, (vs->size - 1) >> 32); + + if (ch->cid >= 0) { + nv_wr32(ch->dev, 0x3000 + ch->cid * 8, (0x4 << 28) | ch->bo->start >> 12); + spin_lock_irqsave(&dev_priv->chan->ch_lock, flags); + ch->handle = ch->bo->start >> 12; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + } + dev_priv->vm->bar_flush(ch->dev); + return 0; +} + +void nvc0_chan_free(struct pscnv_chan *ch) +{ + struct drm_nouveau_private *dev_priv = ch->dev->dev_private; + unsigned long flags; + spin_lock_irqsave(&dev_priv->chan->ch_lock, flags); + ch->handle = 0; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + pscnv_mem_free(ch->bo); +} + +void +nvc0_chan_takedown(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_chan_engine *che = nvc0_ch(dev_priv->chan); + kfree(che); +} + +int +nvc0_chan_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_chan_engine *che = kzalloc(sizeof *che, GFP_KERNEL); + if (!che) { + NV_ERROR(dev, "CH: Couldn't alloc engine\n"); + return -ENOMEM; + } + nv_wr32(dev, 0x200, nv_rd32(dev, 0x200) & 0xfffffeff); + nv_wr32(dev, 0x200, nv_rd32(dev, 0x200) | 0x00000100); + che->base.takedown = nvc0_chan_takedown; + che->base.do_chan_new = nvc0_chan_new; + che->base.do_chan_free = nvc0_chan_free; + dev_priv->chan = &che->base; + spin_lock_init(&dev_priv->chan->ch_lock); + dev_priv->chan->ch_min = 1; + dev_priv->chan->ch_max = 126; + return 0; +} diff --git a/driver/pscnv/nvc0_chan.h b/driver/pscnv/nvc0_chan.h new file mode 100644 index 00000000..f2efeb96 --- /dev/null +++ b/driver/pscnv/nvc0_chan.h @@ -0,0 +1,14 @@ +#ifndef __NVC0_CHAN_H__ +#define __NVC0_CHAN_H__ + +#include "drmP.h" +#include "drm.h" +#include "pscnv_chan.h" + +#define nvc0_ch(x) container_of(x, struct nvc0_chan_engine, base) + +struct nvc0_chan_engine { + struct pscnv_chan_engine base; +}; + +#endif /* __NVC0_CHAN_H__ */ diff --git a/driver/pscnv/nvc0_copy.c b/driver/pscnv/nvc0_copy.c new file mode 100644 index 00000000..8d8d42ba --- /dev/null +++ b/driver/pscnv/nvc0_copy.c @@ -0,0 +1,254 @@ +/* + * Copyright 2011 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "pscnv_engine.h" +#include "pscnv_chan.h" +#include "nvc0_copy.h" +#include "nvc0_copy.fuc.h" +#include "nvc0_vm.h" + +struct nvc0_copy_chan { + struct pscnv_bo *bo; + struct pscnv_mm_node *vm; +}; + +static int +nvc0_copy_chan_alloc(struct pscnv_engine *eng, struct pscnv_chan *ch) +{ + struct drm_device *dev = eng->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_copy_engine *pcopy = NVC0_COPY(eng); + struct nvc0_copy_chan *coch = kzalloc(sizeof(*coch), GFP_KERNEL); + uint32_t cookie = pcopy->fuc; + int ret; + + coch->bo = pscnv_mem_alloc(dev, 256, PSCNV_GEM_CONTIG, 0, cookie); + if (!coch->bo) { + ret = -ENOMEM; + goto fail_mem_alloc; + } + + ret = dev_priv->vm->map_kernel(coch->bo); + if (ret) { + goto fail_map_kernel; + } + + ret = pscnv_vspace_map(ch->vspace, coch->bo, 0x1000, (1ULL << 40) - 1, 0, + &coch->vm); + if (ret) { + goto fail_vspace_map; + } + + nv_wv32(ch->bo, pcopy->ctx + 0, coch->vm->start); + nv_wv32(ch->bo, pcopy->ctx + 4, coch->vm->start >> 32); + dev_priv->vm->bar_flush(dev); + + ch->engdata[PSCNV_ENGINE_COPY + pcopy->id] = coch; + + return 0; + +fail_vspace_map: +fail_map_kernel: + pscnv_mem_free(coch->bo); +fail_mem_alloc: + kfree(coch); + + return ret; +} + +void +nvc0_copy_chan_kill(struct pscnv_engine *eng, struct pscnv_chan *ch) +{ + /* FIXME */ +} + +static void +nvc0_copy_chan_free(struct pscnv_engine *eng, struct pscnv_chan *ch) +{ + struct drm_device *dev = eng->dev; + struct nvc0_copy_engine *pcopy = NVC0_COPY(eng); + struct nvc0_copy_chan *coch = ch->engdata[PSCNV_ENGINE_COPY + pcopy->id]; + uint32_t inst; + + inst = (ch->bo->start >> 12); + inst |= 0x40000000; + + /* disable fifo access */ + nv_wr32(dev, pcopy->fuc + 0x048, 0x00000000); + /* mark channel as unloaded if it's currently active */ + if (nv_rd32(dev, pcopy->fuc + 0x050) == inst) + nv_mask(dev, pcopy->fuc + 0x050, 0x40000000, 0x00000000); + /* mark next channel as invalid if it's about to be loaded */ + if (nv_rd32(dev, pcopy->fuc + 0x054) == inst) + nv_mask(dev, pcopy->fuc + 0x054, 0x40000000, 0x00000000); + /* restore fifo access */ + nv_wr32(dev, pcopy->fuc + 0x048, 0x00000003); + + nv_wv32(ch->bo, pcopy->ctx + 0, 0x00000000); + nv_wv32(ch->bo, pcopy->ctx + 4, 0x00000000); + + pscnv_vspace_unmap_node(coch->vm); + pscnv_mem_free(coch->bo); + kfree(coch); + + ch->engdata[PSCNV_ENGINE_COPY + pcopy->id] = NULL; +} + +void +nvc0_copy_takedown(struct pscnv_engine *eng) +{ + struct drm_device *dev = eng->dev; + struct nvc0_copy_engine *pcopy = NVC0_COPY(eng); + + nv_mask(dev, pcopy->fuc + 0x048, 0x00000003, 0x00000000); + + /* trigger fuc context unload */ + nv_wait(dev, pcopy->fuc + 0x008, 0x0000000c, 0x00000000); + nv_mask(dev, pcopy->fuc + 0x054, 0x40000000, 0x00000000); + nv_wr32(dev, pcopy->fuc + 0x000, 0x00000008); + nv_wait(dev, pcopy->fuc + 0x008, 0x00000008, 0x00000000); + + nv_wr32(dev, pcopy->fuc + 0x014, 0xffffffff); + + nouveau_irq_unregister(dev, pcopy->irq); + kfree(pcopy); +} + +struct pscnv_copy_enum { + int value; + const char *name; +}; + +struct pscnv_copy_enum nvc0_copy_isr_error_name[] = { + { 0x0001, "ILLEGAL_MTHD" }, + { 0x0002, "INVALID_ENUM" }, + { 0x0003, "INVALID_BITFIELD" }, + {} +}; + +static void +nvc0_copy_isr(struct drm_device *dev, int engine) +{ + uint64_t inst; + uint32_t disp, stat, chid, ssta, addr, mthd, subc, data; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_copy_engine *pcopy = NVC0_COPY(dev_priv->engines[engine]); +#define PCOPY_ERROR(name) \ + NV_ERROR(dev, "%s: st %08x ch %d sub %d mthd %04x data %08x %08x/%08llx\n",\ + name, stat, chid, subc, mthd, data, ssta, inst); + + disp = nv_rd32(dev, pcopy->fuc + 0x01c); + stat = nv_rd32(dev, pcopy->fuc + 0x008) & disp & ~(disp >> 16); + inst = (u64)(nv_rd32(dev, pcopy->fuc + 0x050) & 0x0fffffff) << 12; + chid = -1; + ssta = nv_rd32(dev, pcopy->fuc + 0x040) & 0x0000ffff; + addr = nv_rd32(dev, pcopy->fuc + 0x040) >> 16; + mthd = (addr & 0x07ff) << 2; + subc = (addr & 0x3800) >> 11; + data = nv_rd32(dev, pcopy->fuc + 0x044); + + if (stat & 0x00000040) { + PCOPY_ERROR("PCOPY_DISPATCH"); + nv_wr32(dev, pcopy->fuc + 0x004, 0x00000040); + stat &= ~0x00000040; + } + + if (stat) { + NV_INFO(dev, "PCOPY: unhandled intr 0x%08x\n", stat); + nv_wr32(dev, pcopy->fuc + 0x004, stat); + } +} + +static void +nvc0_copy_isr_0(struct drm_device *dev, int irq) +{ + nvc0_copy_isr(dev, PSCNV_ENGINE_COPY0); +} + +static void +nvc0_copy_isr_1(struct drm_device *dev, int irq) +{ + nvc0_copy_isr(dev, PSCNV_ENGINE_COPY1); +} + +int +nvc0_copy_init(struct drm_device *dev, int engine) +{ + int i; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_copy_engine *pcopy = kzalloc(sizeof(*pcopy), GFP_KERNEL); + + if (!pcopy) { + NV_ERROR(dev, "PCOPY%d: Couldn't allocate engine!\n", engine); + return -ENOMEM; + } + NV_INFO(dev, "PCOPY%d: Initializing...\n", engine); + + dev_priv->engines[PSCNV_ENGINE_COPY + engine] = &pcopy->base; + pcopy->base.dev = dev; + pcopy->base.takedown = nvc0_copy_takedown; + pcopy->base.chan_alloc = nvc0_copy_chan_alloc; + pcopy->base.chan_kill = nvc0_copy_chan_kill; + pcopy->base.chan_free = nvc0_copy_chan_free; + spin_lock_init(&pcopy->lock); + + if (engine == 0) { + pcopy->irq = 5; + pcopy->pmc = 0x00000040; + pcopy->fuc = 0x104000; + pcopy->ctx = 0x0230; + nouveau_irq_register(dev, pcopy->irq, nvc0_copy_isr_0); + } else { + pcopy->irq = 6; + pcopy->pmc = 0x00000080; + pcopy->fuc = 0x105000; + pcopy->ctx = 0x0240; + nouveau_irq_register(dev, pcopy->irq, nvc0_copy_isr_1); + } + pcopy->id = engine; + + nv_mask(dev, 0x000200, pcopy->pmc, 0x00000000); + nv_mask(dev, 0x000200, pcopy->pmc, pcopy->pmc); + nv_wr32(dev, pcopy->fuc + 0x014, 0xffffffff); + + nv_wr32(dev, pcopy->fuc + 0x1c0, 0x01000000); + for (i = 0; i < sizeof(nvc0_pcopy_data) / 4; i++) + nv_wr32(dev, pcopy->fuc + 0x1c4, nvc0_pcopy_data[i]); + + nv_wr32(dev, pcopy->fuc + 0x180, 0x01000000); + for (i = 0; i < sizeof(nvc0_pcopy_code) / 4; i++) { + if ((i & 0x3f) == 0) + nv_wr32(dev, pcopy->fuc + 0x188, i >> 6); + nv_wr32(dev, pcopy->fuc + 0x184, nvc0_pcopy_code[i]); + } + + nv_wr32(dev, pcopy->fuc + 0x084, engine - PSCNV_ENGINE_COPY); + nv_wr32(dev, pcopy->fuc + 0x10c, 0x00000000); + nv_wr32(dev, pcopy->fuc + 0x104, 0x00000000); /* ENTRY */ + nv_wr32(dev, pcopy->fuc + 0x100, 0x00000002); /* TRIGGER */ + + return 0; +} diff --git a/driver/pscnv/nvc0_copy.fuc.h b/driver/pscnv/nvc0_copy.fuc.h new file mode 100644 index 00000000..41990388 --- /dev/null +++ b/driver/pscnv/nvc0_copy.fuc.h @@ -0,0 +1,527 @@ +uint32_t nvc0_pcopy_data[] = { + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00010000, + 0x00000000, + 0x00000000, + 0x00010040, + 0x0001019f, + 0x00000000, + 0x00010050, + 0x000101a1, + 0x00000000, + 0x00070080, + 0x0000001c, + 0xfffff000, + 0x00000020, + 0xfff80000, + 0x00000024, + 0xffffe000, + 0x00000028, + 0xfffff800, + 0x0000002c, + 0xfffff000, + 0x00000030, + 0xfff80000, + 0x00000034, + 0xffffe000, + 0x00070088, + 0x00000048, + 0xfffff000, + 0x0000004c, + 0xfff80000, + 0x00000050, + 0xffffe000, + 0x00000054, + 0xfffff800, + 0x00000058, + 0xfffff000, + 0x0000005c, + 0xfff80000, + 0x00000060, + 0xffffe000, + 0x000200c0, + 0x000104b8, + 0x00000000, + 0x00010541, + 0x00000000, + 0x000e00c3, + 0x00000010, + 0xffffff00, + 0x00000014, + 0x0000000f, + 0x0000003c, + 0xffffff00, + 0x00000040, + 0x0000000f, + 0x00000018, + 0xfff80000, + 0x00000044, + 0xfff80000, + 0x00000074, + 0xffff0000, + 0x00000078, + 0xffffe000, + 0x00000068, + 0xfccc0000, + 0x0000006c, + 0x00000000, + 0x00000070, + 0x00000000, + 0x00000004, + 0xffffff00, + 0x00000008, + 0x00000000, + 0x0000000c, + 0x00000000, + 0x00000800, +}; + +uint32_t nvc0_pcopy_code[] = { + 0x04fe04bd, + 0x3517f000, + 0xf10010fe, + 0xf1040017, + 0xf0fff327, + 0x22d00023, + 0x0c25f0c0, + 0xf40012d0, + 0x17f11031, + 0x27f01200, + 0x0012d003, + 0xf40031f4, + 0x0ef40028, + 0x8001cffd, + 0xf40812c4, + 0x21f4060b, + 0x0412c4ca, + 0xf5070bf4, + 0xc4010221, + 0x01d00c11, + 0xf101f840, + 0xfe770047, + 0x47f1004b, + 0x44cf2100, + 0x0144f000, + 0xb60444b6, + 0xf7f13040, + 0xf4b6061c, + 0x1457f106, + 0x00f5d101, + 0xb6043594, + 0x57fe0250, + 0x0145fe00, + 0x010052b7, + 0x00ff67f1, + 0x56fd60bd, + 0x0253f004, + 0xf80545fa, + 0x0053f003, + 0xd100e7f0, + 0x549800fe, + 0x0845b600, + 0xb6015698, + 0x46fd1864, + 0x0047fe05, + 0xf00204b9, + 0x01f40643, + 0x0604fa09, + 0xfa060ef4, + 0x03f80504, + 0x27f100f8, + 0x23cf1400, + 0x1e3fc800, + 0xf4170bf4, + 0x21f40132, + 0x1e3af053, + 0xf00023d0, + 0x24d00147, + 0xcf00f880, + 0x3dc84023, + 0x090bf41e, + 0xf40131f4, + 0x37f05321, + 0x8023d002, + 0x37f100f8, + 0x32cf1900, + 0x0033cf40, + 0x07ff24e4, + 0xf11024b6, + 0xbd010057, + 0x5874bd64, + 0x57580056, + 0x0450b601, + 0xf40446b8, + 0x76bb4d08, + 0x0447b800, + 0xbb0f08f4, + 0x74b60276, + 0x0057bb03, + 0xbbdf0ef4, + 0x44b60246, + 0x0045bb03, + 0xfd014598, + 0x54b00453, + 0x201bf400, + 0x58004558, + 0x64b00146, + 0x091bf400, + 0xf4005380, + 0x32f4300e, + 0xf455f901, + 0x0ef40c01, + 0x0225f025, + 0xf10125f0, + 0xd0100047, + 0x43d00042, + 0x4027f040, + 0xcf0002d0, + 0x24f08002, + 0x0024b040, + 0xf1f71bf4, + 0xf01d0027, + 0x23d00137, + 0xf800f800, + 0x0027f100, + 0xf034bd22, + 0x23d00233, + 0xf400f800, + 0x01b0f030, + 0x0101b000, + 0xb00201b0, + 0x04980301, + 0x3045c71a, + 0xc70150b6, + 0x60b63446, + 0x3847c701, + 0xf40170b6, + 0x84bd0232, + 0x4ac494bd, + 0x0445b60f, + 0xa430b4bd, + 0x0f18f404, + 0xbbc0a5ff, + 0x31f400cb, + 0x220ef402, + 0xf00c1bf4, + 0xcbbb10c7, + 0x160ef400, + 0xf406a430, + 0xc7f00c18, + 0x00cbbb14, + 0xf1070ef4, + 0x380080c7, + 0x80b601c8, + 0x01b0b601, + 0xf404b5b8, + 0x90b6c308, + 0x0497b801, + 0xfdb208f4, + 0x06800065, + 0x1d08980e, + 0xf40068fd, + 0x64bd0502, + 0x800075fd, + 0x78fd1907, + 0x1057f100, + 0x0654b608, + 0xd00056d0, + 0x50b74057, + 0x06980800, + 0x0162b619, + 0x980864b6, + 0x72b60e07, + 0x0567fd01, + 0xb70056d0, + 0xb4010050, + 0x56d00060, + 0x0160b400, + 0xb44056d0, + 0x56d00260, + 0x0360b480, + 0xb7c056d0, + 0x98040050, + 0x56d01b06, + 0x1c069800, + 0xf44056d0, + 0x00f81030, + 0xc7075798, + 0x78c76879, + 0x0380b664, + 0xb06077c7, + 0x1bf40e76, + 0x0477f009, + 0xf00f0ef4, + 0x70b6027c, + 0x0947fd11, + 0x980677f0, + 0x5b980c5a, + 0x00abfd0e, + 0xbb01b7f0, + 0xb2b604b7, + 0xc4abff01, + 0x9805a7bb, + 0xe7f00d5d, + 0x04e8bb01, + 0xff01e2b6, + 0xd8bbb4de, + 0x01e0b605, + 0xbb0cef94, + 0xfefd02eb, + 0x026cf005, + 0x020860b7, + 0xd00864b6, + 0xb7bb006f, + 0x00cbbb04, + 0x98085f98, + 0xfbfd0e5b, + 0x01b7f000, + 0xb604b7bb, + 0xfbbb01b2, + 0x05f7bb00, + 0x5f98f0f9, + 0x01b7f009, + 0xb604b8bb, + 0xfbbb01b2, + 0x05f8bb00, + 0x78bbf0f9, + 0x0282b600, + 0xbb01b7f0, + 0xb9bb04b8, + 0x0b589804, + 0xbb01e7f0, + 0xe2b604e9, + 0xf48eff01, + 0xbb04f7bb, + 0x79bb00cf, + 0x0589bb00, + 0x90fcf0fc, + 0xbb00d9fd, + 0x89fd00ad, + 0x008ffd00, + 0xbb00a8bb, + 0x92b604a7, + 0x0497bb01, + 0x988069d0, + 0x58980557, + 0x00acbb04, + 0xb6007abb, + 0x84b60081, + 0x058bfd10, + 0x060062b7, + 0xb70067d0, + 0xd0040060, + 0x00f80068, + 0xb7026cf0, + 0xb6020260, + 0x57980864, + 0x0067d005, + 0x040060b7, + 0xb6045798, + 0x67d01074, + 0x0060b700, + 0x06579804, + 0xf80067d0, + 0xf900f900, + 0x0007f110, + 0x0604b608, + 0xf00001cf, + 0x1bf40114, + 0xfc10fcfa, + 0xc800f800, + 0x1bf40d34, + 0xd121f570, + 0x0c47f103, + 0x0644b608, + 0xb6020598, + 0x45d00450, + 0x4040d000, + 0xd00c57f0, + 0x40b78045, + 0x05980400, + 0x1054b601, + 0xb70045d0, + 0xf1050040, + 0xf00b0057, + 0x45d00153, + 0x4057f100, + 0x0154b640, + 0x808053f1, + 0xf14045d0, + 0xf1111057, + 0xd0131253, + 0x57f18045, + 0x53f11514, + 0x45d01716, + 0x0157f1c0, + 0x0153f026, + 0x080047f1, + 0xd00644b6, + 0x21f50045, + 0x47f103d1, + 0x44b6080c, + 0x02059806, + 0xd00045d0, + 0x57f04040, + 0x8045d004, + 0x040040b7, + 0xb6010598, + 0x45d01054, + 0x0040b700, + 0x0057f105, + 0x0045d003, + 0x111057f1, + 0x131253f1, + 0x984045d0, + 0x40b70305, + 0x45d00500, + 0x0157f100, + 0x0153f026, + 0x080047f1, + 0xd00644b6, + 0x00f80045, + 0x03d121f5, + 0xf4003fc8, + 0x21f50e0b, + 0x47f101af, + 0x0ef40200, + 0x1067f11e, + 0x0664b608, + 0x800177f0, + 0x07800e07, + 0x1d079819, + 0xd00067d0, + 0x44bd4067, + 0xbd0232f4, + 0x043fc854, + 0xf50a0bf4, + 0xf403a821, + 0x21f50a0e, + 0x49f0029c, + 0x0231f407, + 0xc82c57f0, + 0x0bf4083f, + 0xa821f50a, + 0x0a0ef403, + 0x029c21f5, + 0xf10849f0, + 0xb6080057, + 0x06980654, + 0x4056d01e, + 0xf14167f0, + 0xfd440063, + 0x54d00546, + 0x0c3fc800, + 0xf5070bf4, + 0xf803eb21, + 0x0027f100, + 0xf034bd22, + 0x23d00133, + 0x0000f800, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, + 0x00000000, +}; diff --git a/driver/pscnv/nvc0_copy.h b/driver/pscnv/nvc0_copy.h new file mode 100644 index 00000000..3ec83a0a --- /dev/null +++ b/driver/pscnv/nvc0_copy.h @@ -0,0 +1,37 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +#ifndef __NVC0_COPY_H__ +#define __NVC0_COPY_H__ + +#define NVC0_COPY(x) container_of(x, struct nvc0_copy_engine, base) + +struct nvc0_copy_engine { + struct pscnv_engine base; + spinlock_t lock; + uint32_t irq; + uint32_t pmc; + uint32_t fuc; + uint32_t ctx; + int id; +}; + +#endif diff --git a/driver/pscnv/nvc0_ctxctl.h b/driver/pscnv/nvc0_ctxctl.h new file mode 100644 index 00000000..32559405 --- /dev/null +++ b/driver/pscnv/nvc0_ctxctl.h @@ -0,0 +1,2999 @@ + +#ifndef NVC0_CTXCTL_H__ +#define NVC0_CTXCTL_H__ + +typedef unsigned char uint8_t; + +static const uint8_t nvc0_ctxctl_data_1a[] = +{ + 0x4d, 0x61, 0x72, 0x20, 0x20, 0x31, 0x20, 0x32, + 0x30, 0x31, 0x30, 0x00, 0x31, 0x30, 0x3a, 0x32, + 0x39, 0x3a, 0x33, 0x39, 0x00, 0x00, 0x00, 0x00, + 0xa0, 0x86, 0x01, 0x00, 0x00, 0x10, 0x00, 0x00, + 0x80, 0x03, 0x00, 0x00, 0x00, 0x04, 0x00, 0x14, + 0x50, 0x04, 0x00, 0x20, 0x00, 0x06, 0x00, 0x00, + 0x84, 0x06, 0x00, 0x00, 0x00, 0x07, 0x00, 0x10, + 0x00, 0x08, 0x00, 0x00, 0x08, 0x08, 0x00, 0x08, + 0x28, 0x08, 0x00, 0x00, 0x30, 0x08, 0x00, 0x00, + 0xd8, 0x08, 0x00, 0x00, 0xe0, 0x08, 0x00, 0x00, + 0xe8, 0x08, 0x00, 0x14, 0x1c, 0x09, 0x00, 0x00, + 0x24, 0x09, 0x00, 0x08, 0x00, 0x0b, 0x00, 0x00, + 0x08, 0x0b, 0x00, 0x14, 0xb8, 0x0b, 0x00, 0x00, + 0x08, 0x0c, 0x00, 0x00, 0x10, 0x0c, 0x00, 0x1c, + 0x80, 0x0c, 0x00, 0x00, 0x8c, 0x0c, 0x00, 0x00, + 0x00, 0x10, 0x00, 0x08, 0x14, 0x10, 0x00, 0x00, + 0x18, 0x00, 0x00, 0x00, 0x48, 0x00, 0x00, 0x00, + 0x64, 0x00, 0x00, 0x00, 0x88, 0x00, 0x00, 0x00, + 0x00, 0x02, 0x00, 0x14, 0x1c, 0x02, 0x00, 0x04, + 0x00, 0x03, 0x00, 0x14, 0xd0, 0x03, 0x00, 0x00, + 0xe0, 0x03, 0x00, 0x04, 0x00, 0x04, 0x00, 0x08, + 0x20, 0x04, 0x00, 0x00, 0xe8, 0x04, 0x00, 0x00, + 0xf4, 0x04, 0x00, 0x00, 0x20, 0x05, 0x00, 0x04, + 0x04, 0x06, 0x00, 0x0c, 0x44, 0x06, 0x00, 0x4c, + 0x98, 0x06, 0x00, 0x00, 0x50, 0x07, 0x00, 0x04, + 0x11, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x18, + 0x20, 0x0a, 0x00, 0x18, 0x40, 0x0a, 0x00, 0x18, + 0x60, 0x0a, 0x00, 0x18, 0x80, 0x0a, 0x00, 0x18, + 0xa0, 0x0a, 0x00, 0x18, 0xc0, 0x0a, 0x00, 0x18, + 0xe0, 0x0a, 0x00, 0x18, 0x08, 0x00, 0x00, 0x00, + 0x84, 0x03, 0x00, 0x00, 0xa0, 0x04, 0x00, 0x00, + 0x04, 0x06, 0x00, 0x00, 0x80, 0x06, 0x00, 0x00, + 0x14, 0x07, 0x00, 0x00, 0x1c, 0x08, 0x00, 0x00, + 0xc8, 0x08, 0x00, 0x00, 0x04, 0x0b, 0x00, 0x00, + 0x08, 0x00, 0x00, 0x00, 0x54, 0x00, 0x00, 0x00, + 0x0c, 0x04, 0x00, 0x00, 0xa8, 0x04, 0x00, 0x00, + 0x00, 0x06, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, + 0x40, 0x00, 0x00, 0x7c, 0xc0, 0x00, 0x00, 0x40, + 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14, + 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 +}; + +static const uint8_t nvc0_ctxctl_data_09[] = +{ + 0x4d, 0x61, 0x72, 0x20, 0x20, 0x31, 0x20, 0x32, + 0x30, 0x31, 0x30, 0x00, 0x31, 0x30, 0x3a, 0x32, + 0x39, 0x3a, 0x33, 0x32, 0x00, 0x00, 0x00, 0x00, + 0xa0, 0x86, 0x01, 0x00, 0x00, 0x10, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x07, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x02, 0x00, 0x00, 0x00, 0x1c, 0xe9, 0x17, 0x04, + 0x04, 0x02, 0x40, 0x04, 0x04, 0x40, 0x40, 0x28, + 0x44, 0x40, 0x40, 0x00, 0x94, 0x40, 0x40, 0x34, + 0xd0, 0x40, 0x40, 0x18, 0xf8, 0x40, 0x40, 0x00, + 0x30, 0x41, 0x40, 0x08, 0x50, 0x41, 0x40, 0x08, + 0x64, 0x41, 0x40, 0x04, 0x74, 0x41, 0x40, 0x08, + 0x00, 0x42, 0x40, 0x1c, 0x04, 0x44, 0x40, 0x34, + 0x60, 0x44, 0x40, 0x0c, 0x80, 0x44, 0x40, 0x00, + 0x98, 0x44, 0x40, 0x00, 0x04, 0x46, 0x40, 0x0c, + 0x18, 0x46, 0x40, 0x7c, 0x98, 0x46, 0x40, 0x50, + 0xf0, 0x46, 0x40, 0x04, 0x00, 0x47, 0x40, 0x54, + 0x00, 0x58, 0x40, 0x00, 0x30, 0x58, 0x40, 0x08, + 0x54, 0x58, 0x40, 0x00, 0x70, 0x58, 0x40, 0x0c, + 0x00, 0x5a, 0x40, 0x04, 0x18, 0x5a, 0x40, 0x00, + 0x20, 0x60, 0x40, 0x00, 0x28, 0x60, 0x40, 0x0c, + 0xa8, 0x64, 0x40, 0x04, 0xb4, 0x64, 0x40, 0x04, + 0x04, 0x78, 0x40, 0x00, 0x0c, 0x78, 0x40, 0x14, + 0xbc, 0x78, 0x40, 0x00, 0x00, 0x80, 0x40, 0x18, + 0x64, 0x80, 0x40, 0x00, 0x00, 0x88, 0x40, 0x08, + 0x00, 0x89, 0x40, 0x0c, 0x80, 0x89, 0x40, 0x00, + 0x27, 0x00, 0x00, 0x00, 0x5c, 0x41, 0x40, 0x00, + 0x08, 0x78, 0x40, 0x00, 0x14, 0x89, 0x40, 0x1c, + 0x88, 0x89, 0x40, 0x04, 0x40, 0x00, 0x1b, 0x7c, + 0xc0, 0x00, 0x1b, 0x40, 0x40, 0x02, 0x1b, 0x7c, + 0xc0, 0x02, 0x1b, 0x40, 0x40, 0x04, 0x1b, 0x7c, + 0xc0, 0x04, 0x1b, 0x40, 0x40, 0x06, 0x1b, 0x7c, + 0xc0, 0x06, 0x1b, 0x40, 0x40, 0x08, 0x1b, 0x7c, + 0xc0, 0x08, 0x1b, 0x40, 0x40, 0x0a, 0x1b, 0x7c, + 0xc0, 0x0a, 0x1b, 0x40, 0x40, 0x0c, 0x1b, 0x7c, + 0xc0, 0x0c, 0x1b, 0x40, 0x40, 0x0e, 0x1b, 0x7c, + 0xc0, 0x0e, 0x1b, 0x40, 0x00, 0x40, 0x1b, 0x08, + 0x10, 0x40, 0x1b, 0x08, 0x20, 0x40, 0x1b, 0x08, + 0x30, 0x40, 0x1b, 0x08, 0x40, 0x40, 0x1b, 0x08, + 0x50, 0x40, 0x1b, 0x08, 0x60, 0x40, 0x1b, 0x0c, + 0x74, 0x40, 0x1b, 0x08, 0x90, 0x40, 0x1b, 0x0c, + 0xa4, 0x40, 0x1b, 0x00, 0x00, 0x41, 0x1b, 0x14, + 0x00, 0xe0, 0x1b, 0x14, 0x20, 0x00, 0x00, 0x00, + 0x40, 0x00, 0x00, 0x7c, 0xc0, 0x00, 0x00, 0x40, + 0x40, 0x02, 0x00, 0x7c, 0xc0, 0x02, 0x00, 0x40, + 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14, + 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 +}; + +static const uint8_t nvc0_ctxctl_code_1a[] = +{ + 0xf1, 0x07, 0x00, 0x08, 0xf1, 0x03, 0x00, 0x00, + 0xfe, 0x04, 0x00, 0xbd, 0xa4, 0xf5, 0x21, 0x9a, + 0x19, 0xf8, 0x02, 0xf9, 0x90, 0xf9, 0xa0, 0xf9, + 0xb0, 0xf9, 0xc0, 0xf9, 0xd0, 0xf9, 0xe0, 0xf9, + 0xf0, 0xfe, 0x8a, 0x01, 0xf9, 0xa0, 0xf5, 0x21, + 0xe0, 0x0a, 0xfc, 0xa0, 0xfe, 0xa8, 0x00, 0xf4, + 0x32, 0x02, 0xfc, 0xf0, 0xfc, 0xe0, 0xfc, 0xd0, + 0xfc, 0xc0, 0xfc, 0xb0, 0xfc, 0xa0, 0xfc, 0x90, + 0xf8, 0x01, 0xf8, 0x00, 0xf1, 0x97, 0x5c, 0x01, + 0x80, 0x9b, 0x00, 0xf8, 0x00, 0xf1, 0x97, 0x70, + 0x01, 0x80, 0x9b, 0x00, 0xf8, 0x00, 0xf1, 0x97, + 0x74, 0x01, 0x80, 0x9b, 0x00, 0xf8, 0x00, 0xf1, + 0x97, 0x78, 0x01, 0x80, 0x9b, 0x00, 0xf8, 0x00, + 0xf1, 0x97, 0x7c, 0x01, 0x80, 0x9b, 0x00, 0xf8, + 0x00, 0xf1, 0x97, 0x50, 0x01, 0x98, 0x99, 0x00, + 0xf1, 0xb4, 0xff, 0xff, 0xc7, 0x99, 0xe8, 0xb6, + 0x94, 0x10, 0xfd, 0xb9, 0x05, 0xf1, 0x97, 0x00, + 0x03, 0x80, 0x9b, 0x28, 0xf8, 0x00, 0xf1, 0x97, + 0x58, 0x01, 0x98, 0x99, 0x00, 0xf1, 0xb4, 0xff, + 0xff, 0xc7, 0x99, 0xe8, 0xb6, 0x94, 0x10, 0xfd, + 0xb9, 0x05, 0xf1, 0x97, 0x00, 0x03, 0x80, 0x9b, + 0x3a, 0xf8, 0x00, 0xf1, 0x97, 0xe0, 0x00, 0xb0, + 0xa6, 0x03, 0xf4, 0x1b, 0x1f, 0xf1, 0x97, 0x84, + 0x01, 0x98, 0x9f, 0x00, 0x94, 0xfe, 0x03, 0x94, + 0xf9, 0x06, 0xbb, 0x9e, 0x02, 0xbb, 0x9f, 0x02, + 0xb6, 0x90, 0x40, 0xb6, 0x94, 0x02, 0xf4, 0x0e, + 0x21, 0xb0, 0xa6, 0x05, 0xf4, 0x0b, 0x1b, 0xb0, + 0xa6, 0x06, 0xf4, 0x0b, 0x08, 0xbd, 0x94, 0xf4, + 0x0e, 0x10, 0xf1, 0x97, 0x84, 0x01, 0x98, 0x99, + 0x00, 0xb6, 0x94, 0x04, 0xb6, 0x90, 0xfc, 0x97, + 0x9a, 0x08, 0xb6, 0xa0, 0x01, 0xb6, 0xa4, 0x08, + 0xf8, 0x00, 0xf1, 0x97, 0xfc, 0x47, 0xf0, 0x93, + 0x02, 0xfa, 0x9a, 0x00, 0xf1, 0xf7, 0xfc, 0x4a, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x03, 0xfa, 0xf9, + 0x00, 0xf8, 0x00, 0xf1, 0x97, 0xfc, 0x47, 0xf0, + 0x93, 0x02, 0xfa, 0x9a, 0x00, 0xf1, 0xf7, 0xfc, + 0x4a, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x04, 0xfa, + 0xf9, 0x00, 0xf8, 0x00, 0xf1, 0xd7, 0xfc, 0x4a, + 0xf0, 0xd3, 0x02, 0xf0, 0xe7, 0x0c, 0xf0, 0x97, + 0x0d, 0xb0, 0xa6, 0x00, 0xf4, 0x0b, 0x08, 0xfa, + 0xde, 0x00, 0xf8, 0x00, 0xfa, 0xd9, 0x00, 0xf8, + 0x00, 0xf1, 0x97, 0xfc, 0x4f, 0xf0, 0x93, 0x02, + 0xfa, 0x9a, 0x00, 0xb0, 0xb6, 0x00, 0xf4, 0x0b, + 0x10, 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, 0x02, + 0xf0, 0x97, 0x0a, 0xf4, 0x0e, 0x0d, 0xf1, 0xf7, + 0xfc, 0x4a, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x0b, + 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf1, 0xf7, 0x00, + 0x85, 0xf0, 0xf3, 0x01, 0xf0, 0x97, 0x20, 0xfa, + 0xf9, 0x00, 0xf1, 0x97, 0x1c, 0x02, 0x92, 0xaf, + 0x00, 0x80, 0x9a, 0x00, 0xf4, 0x0e, 0x06, 0xb6, + 0xf2, 0x01, 0xb0, 0xf6, 0x00, 0xf4, 0x1b, 0xfa, + 0xf1, 0x97, 0x1c, 0x02, 0x80, 0x9f, 0x00, 0xf1, + 0xf7, 0x00, 0x85, 0xf0, 0xf3, 0x01, 0xf1, 0x97, + 0x20, 0x0a, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf1, + 0x97, 0x00, 0x1d, 0xf0, 0x93, 0x02, 0xfa, 0x9b, + 0x00, 0xf0, 0xa4, 0x0f, 0xb7, 0x90, 0x00, 0x01, + 0xfa, 0x9a, 0x00, 0xb7, 0x90, 0x00, 0x0c, 0xfa, + 0x9c, 0x00, 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0c, + 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, 0xf9, 0x00, + 0xf8, 0x00, 0xf0, 0x97, 0xff, 0xf1, 0x93, 0xff, + 0x3f, 0xf0, 0xf7, 0x00, 0xf1, 0xf3, 0x00, 0x80, + 0xff, 0xa9, 0x94, 0xf1, 0xe7, 0x00, 0x0c, 0xf0, + 0xe3, 0x01, 0xfd, 0x9f, 0x05, 0xb0, 0xa6, 0x00, + 0xf4, 0x0b, 0x06, 0xfa, 0xe9, 0x00, 0xf8, 0x00, + 0xf1, 0x97, 0x00, 0xcc, 0xf0, 0x93, 0x01, 0xfa, + 0x9b, 0x00, 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x00, + 0xc0, 0xe7, 0xaa, 0xe2, 0x02, 0xf0, 0xc4, 0x01, + 0xb6, 0xa4, 0x02, 0xfd, 0xc9, 0x05, 0xf1, 0x97, + 0x00, 0xca, 0xf0, 0x93, 0x01, 0xfd, 0xac, 0x05, + 0xfa, 0x9a, 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf1, + 0xf7, 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0x92, 0xd0, + 0x00, 0xf1, 0x97, 0x00, 0x02, 0xb4, 0xd0, 0x02, + 0xfa, 0xf9, 0x00, 0xf0, 0xf7, 0x01, 0xb0, 0xd6, + 0x02, 0xf5, 0x0b, 0x46, 0x00, 0xb8, 0xdf, 0x06, + 0xf4, 0x0b, 0x08, 0xbd, 0xf4, 0xf4, 0x0e, 0x3a, + 0xb0, 0xe6, 0x00, 0xf4, 0x1b, 0x0d, 0xf0, 0xf7, + 0x02, 0xf1, 0xf3, 0x00, 0x80, 0xf4, 0x0e, 0x2a, + 0xb0, 0xe6, 0x03, 0xf4, 0x1b, 0x0d, 0xf0, 0xf7, + 0x03, 0xf1, 0xf3, 0x00, 0x80, 0xf4, 0x0e, 0x1a, + 0xb0, 0xe6, 0x02, 0xf4, 0x1b, 0x0d, 0xf0, 0xf7, + 0x04, 0xf1, 0xf3, 0x00, 0x80, 0xf4, 0x0e, 0x0a, + 0xf0, 0xf7, 0x00, 0xf1, 0xf3, 0x00, 0x80, 0xf1, + 0x97, 0x00, 0x88, 0xf0, 0x93, 0x02, 0xfa, 0x9f, + 0x00, 0xfe, 0xa7, 0x00, 0xbd, 0x94, 0xfe, 0x9b, + 0x00, 0xf1, 0xf7, 0x00, 0x43, 0xfa, 0xf9, 0x00, + 0xb4, 0x90, 0x03, 0xb6, 0xc4, 0x10, 0xb0, 0x96, + 0x01, 0xf4, 0x1b, 0x0c, 0xff, 0x0c, 0x95, 0xfa, + 0xb9, 0x05, 0xf4, 0x0e, 0x09, 0xff, 0x0c, 0x95, + 0xfa, 0xb9, 0x06, 0xb4, 0x90, 0x04, 0xb0, 0x96, + 0x02, 0xf4, 0x1b, 0x05, 0xf8, 0x03, 0xf1, 0xf7, + 0x00, 0x88, 0xf0, 0xf3, 0x02, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x02, 0xb7, 0xf2, + 0x00, 0x75, 0xfa, 0xf9, 0x00, 0xfc, 0x00, 0xf8, + 0x00, 0xf4, 0x30, 0xf4, 0xf1, 0xf7, 0x00, 0x0b, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x02, 0xfa, 0xf9, + 0x00, 0xb0, 0x91, 0x00, 0xf1, 0x97, 0x80, 0x01, + 0x98, 0x9b, 0x00, 0xf0, 0x97, 0x02, 0xb0, 0xa1, + 0x02, 0xb0, 0x91, 0x01, 0xbd, 0xa4, 0xf0, 0xc7, + 0x06, 0xf1, 0xd7, 0x00, 0x03, 0xbd, 0xe4, 0xb6, + 0xb4, 0x08, 0xb7, 0xb0, 0x00, 0x02, 0xf5, 0x21, + 0x2d, 0x02, 0xf1, 0xf7, 0x00, 0x13, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x02, 0xfa, 0xf9, 0x00, 0xf4, + 0x30, 0x0c, 0xf8, 0x00, 0xf4, 0x30, 0xf4, 0xf1, + 0xf7, 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x01, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x80, 0x01, + 0x98, 0x9b, 0x00, 0xf0, 0x97, 0x02, 0xb0, 0x91, + 0x00, 0xf0, 0x97, 0x01, 0xb0, 0xa1, 0x02, 0xb0, + 0x91, 0x01, 0xbd, 0xa4, 0xf0, 0xc7, 0x06, 0xf1, + 0xd7, 0x00, 0x03, 0xbd, 0xe4, 0xb6, 0xb4, 0x08, + 0xb7, 0xb0, 0x00, 0x02, 0xf5, 0x21, 0x2d, 0x02, + 0xf1, 0xf7, 0x00, 0x13, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf4, 0x30, 0x0c, + 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x10, 0xfa, + 0xf9, 0x00, 0xf1, 0x97, 0x48, 0x01, 0x98, 0x99, + 0x00, 0xf1, 0xf7, 0x00, 0x03, 0x98, 0xfa, 0x01, + 0xf1, 0xb4, 0xff, 0xff, 0xc7, 0x99, 0xe8, 0xb6, + 0x94, 0x10, 0xbd, 0xc4, 0xfd, 0xb9, 0x05, 0xf0, + 0xd7, 0x14, 0x95, 0xb9, 0x10, 0x80, 0xfb, 0x03, + 0xf1, 0xe7, 0x00, 0x42, 0xf0, 0xe3, 0x02, 0xf1, + 0xb4, 0xff, 0xff, 0xbb, 0xb9, 0x00, 0xf4, 0x0e, + 0x1f, 0x98, 0x99, 0x00, 0x92, 0xef, 0x00, 0xbc, + 0xb9, 0x90, 0xfa, 0xe9, 0x00, 0xb7, 0xf0, 0x00, + 0x01, 0xfa, 0xf9, 0x00, 0xb6, 0xc0, 0x01, 0xb6, + 0xd0, 0x08, 0xb6, 0xe0, 0x04, 0x97, 0xd9, 0x02, + 0xf1, 0xf7, 0x00, 0x03, 0xb6, 0x94, 0x02, 0xbb, + 0x9f, 0x00, 0xb8, 0xca, 0x06, 0xf4, 0x1b, 0xd4, + 0xf1, 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x00, 0xf0, 0x93, 0x10, 0xfa, 0xf9, 0x00, + 0xf8, 0x00, 0xb0, 0xd6, 0x00, 0xf0, 0xfc, 0x0b, + 0xf0, 0xf6, 0x01, 0xf1, 0x97, 0x00, 0xcc, 0xf0, + 0x93, 0x01, 0xb6, 0xf0, 0x02, 0xfa, 0x9b, 0x00, + 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x00, 0x80, 0xf0, + 0xf4, 0x03, 0xf0, 0xc4, 0x01, 0xb6, 0xf4, 0x1d, + 0xe7, 0xaa, 0xe2, 0x02, 0xb6, 0xa4, 0x02, 0xfd, + 0xca, 0x05, 0xfd, 0xc9, 0x05, 0xf1, 0x97, 0x00, + 0xca, 0xf0, 0x93, 0x01, 0xfd, 0xfc, 0x05, 0xfa, + 0x9f, 0x00, 0xf1, 0x97, 0x00, 0xca, 0xf0, 0x93, + 0x01, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf0, 0xf7, + 0x00, 0xf1, 0xf3, 0x00, 0x80, 0xfd, 0x9f, 0x04, + 0xf4, 0x1b, 0xea, 0xb0, 0xd6, 0x00, 0xf4, 0x0b, + 0x14, 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x01, 0xbd, + 0xf4, 0xff, 0x9f, 0x9f, 0xf0, 0x94, 0x80, 0xf4, + 0x0b, 0xf2, 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, + 0x00, 0x85, 0xf0, 0xf3, 0x01, 0x92, 0xa0, 0x00, + 0xf1, 0x97, 0x70, 0x02, 0xfa, 0xf9, 0x00, 0xf1, + 0xa7, 0x14, 0xa6, 0xf0, 0xa3, 0x41, 0xf1, 0xb7, + 0x20, 0x08, 0xbd, 0xc4, 0xf0, 0xd7, 0x01, 0xf5, + 0x21, 0x0a, 0x04, 0xf1, 0x97, 0x18, 0x02, 0x92, + 0x0f, 0x00, 0x80, 0x90, 0x00, 0xf4, 0x0e, 0x06, + 0xb6, 0xf2, 0x01, 0xb0, 0xf6, 0x00, 0xf4, 0x1b, + 0xfa, 0xf1, 0x97, 0x18, 0x02, 0x80, 0x9f, 0x00, + 0xf1, 0xf7, 0x00, 0x85, 0xf0, 0xf3, 0x01, 0xf1, + 0x97, 0x70, 0x07, 0xfa, 0xf9, 0x00, 0xf1, 0xa7, + 0x14, 0xa6, 0xf0, 0xa3, 0x41, 0xf1, 0xb7, 0x20, + 0x0a, 0xbd, 0xc4, 0xf0, 0xd7, 0x01, 0xf5, 0x21, + 0x0a, 0x04, 0xfc, 0x00, 0xf8, 0x00, 0xf0, 0xa7, + 0x08, 0xf5, 0x21, 0x7c, 0x04, 0xf0, 0xf7, 0x00, + 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x01, 0xfa, + 0xf9, 0x00, 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0a, + 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x08, 0xfa, + 0xf9, 0x00, 0xf0, 0xa7, 0x06, 0xf5, 0x21, 0xab, + 0x00, 0xf1, 0xe7, 0x58, 0x01, 0x98, 0xe9, 0x00, + 0xf1, 0xb7, 0x54, 0x01, 0xf1, 0xd7, 0x00, 0x03, + 0x98, 0xbc, 0x00, 0x98, 0xdf, 0x39, 0xbb, 0x9a, + 0x00, 0x80, 0xe9, 0x00, 0xbb, 0xac, 0x00, 0xf0, + 0x97, 0x00, 0xf0, 0x93, 0x02, 0xbb, 0xfa, 0x00, + 0x80, 0xba, 0x00, 0x80, 0xdf, 0x39, 0xfa, 0x9a, + 0x00, 0xf1, 0x97, 0x80, 0x01, 0x98, 0x99, 0x00, + 0xf1, 0xa7, 0x18, 0x94, 0xf0, 0xa3, 0x40, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf0, 0xb7, 0x01, 0xbb, 0xb9, + 0x04, 0xf5, 0x21, 0x0a, 0x04, 0xf1, 0xf7, 0x00, + 0x12, 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x08, + 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf9, 0x00, 0x92, + 0xab, 0x00, 0xf1, 0x07, 0x0a, 0x04, 0xf1, 0xa7, + 0x18, 0x98, 0xf0, 0xa3, 0x40, 0xbd, 0xc4, 0xbd, + 0xd4, 0xf9, 0x05, 0xf1, 0xa7, 0x1c, 0x9c, 0xf0, + 0xa3, 0x40, 0xf0, 0xb7, 0x01, 0xbd, 0xc4, 0xbd, + 0xd4, 0xf9, 0x05, 0xfc, 0x00, 0xf8, 0x00, 0xf5, + 0x21, 0x6d, 0x05, 0xf8, 0x00, 0xf9, 0x00, 0xf1, + 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0x92, 0xa0, + 0x00, 0xf9, 0x10, 0x92, 0xba, 0x00, 0xf0, 0x97, + 0x04, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x14, 0x02, + 0x98, 0x9d, 0x00, 0xf1, 0x97, 0x10, 0x02, 0x98, + 0x99, 0x00, 0xf1, 0xc7, 0xd0, 0x01, 0xc4, 0xdf, + 0x07, 0xf1, 0x17, 0x14, 0x02, 0x94, 0xfe, 0x03, + 0x90, 0xdb, 0x01, 0xbb, 0xec, 0x00, 0xc7, 0x9c, + 0x03, 0xf0, 0x94, 0x07, 0xb8, 0xf9, 0x06, 0xf4, + 0x1b, 0x16, 0xc7, 0xd9, 0x03, 0xb8, 0x9c, 0x06, + 0xf4, 0x0b, 0x0d, 0xf0, 0xa7, 0x12, 0xf5, 0x21, + 0x97, 0x05, 0xf4, 0x0e, 0x17, 0x80, 0xea, 0x01, + 0x80, 0xe0, 0x00, 0x80, 0x1b, 0x00, 0xb0, 0xb6, + 0x10, 0xf4, 0x1b, 0x08, 0xbd, 0x94, 0x80, 0x19, + 0x00, 0xf1, 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, + 0xf0, 0x97, 0x04, 0xfa, 0xf9, 0x00, 0xfc, 0x10, + 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, + 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0x92, 0xa0, 0x00, + 0xf9, 0x10, 0x92, 0xba, 0x00, 0xf0, 0x97, 0x02, + 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0xcc, 0x01, 0x98, + 0x9d, 0x00, 0xf1, 0x97, 0xc8, 0x01, 0x98, 0x99, + 0x00, 0xf1, 0xc7, 0x88, 0x01, 0xc4, 0xdf, 0x07, + 0xf1, 0x17, 0xcc, 0x01, 0x94, 0xfe, 0x03, 0x90, + 0xdb, 0x01, 0xbb, 0xec, 0x00, 0xc7, 0x9c, 0x03, + 0xf0, 0x94, 0x07, 0xb8, 0xf9, 0x06, 0xf4, 0x1b, + 0x16, 0xc7, 0xd9, 0x03, 0xb8, 0x9c, 0x06, 0xf4, + 0x0b, 0x0d, 0xf0, 0xa7, 0x12, 0xf5, 0x21, 0x97, + 0x05, 0xf4, 0x0e, 0x17, 0x80, 0xea, 0x01, 0x80, + 0xe0, 0x00, 0x80, 0x1b, 0x00, 0xb0, 0xb6, 0x10, + 0xf4, 0x1b, 0x08, 0xbd, 0x94, 0x80, 0x19, 0x00, + 0xf1, 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x02, 0xfa, 0xf9, 0x00, 0xfc, 0x10, 0xfc, + 0x00, 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, + 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x01, 0xfa, 0xf9, + 0x00, 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x01, 0xbd, + 0xf4, 0xff, 0x9f, 0x9f, 0xf1, 0x94, 0x00, 0x10, + 0xf4, 0x1b, 0xf1, 0xf1, 0xf7, 0x00, 0x13, 0xf0, + 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x01, 0xfa, 0xf9, + 0x00, 0xf8, 0x00, 0xf9, 0x00, 0x92, 0xa0, 0x00, + 0xf5, 0x21, 0x9b, 0x06, 0xf1, 0x97, 0x00, 0x81, + 0xf0, 0x93, 0x02, 0xfa, 0x90, 0x00, 0xfc, 0x00, + 0xf8, 0x00, 0xf1, 0x97, 0x80, 0x01, 0x98, 0x99, + 0x00, 0xf9, 0x00, 0xbd, 0xd4, 0xf4, 0x30, 0xf4, + 0xb6, 0x94, 0x08, 0xf1, 0xe7, 0x00, 0x04, 0xbd, + 0xf4, 0xa0, 0x90, 0x00, 0x02, 0xf0, 0x97, 0x00, + 0xf1, 0x93, 0x00, 0x80, 0xff, 0xf9, 0x95, 0xb6, + 0xf0, 0x04, 0x80, 0xe9, 0x00, 0xb6, 0xe0, 0x04, + 0xb6, 0xd0, 0x01, 0xb1, 0xd6, 0x40, 0x00, 0xf4, + 0x1b, 0xe6, 0xf1, 0x97, 0x5c, 0x01, 0x98, 0x9a, + 0x00, 0xf5, 0x21, 0xcb, 0x06, 0xf0, 0x97, 0x02, + 0xf0, 0xc7, 0x06, 0xf1, 0xd7, 0x00, 0x04, 0xbd, + 0xe4, 0xb0, 0x91, 0x00, 0xbd, 0xa4, 0x92, 0x0b, + 0x00, 0xb0, 0x91, 0x01, 0xb0, 0x91, 0x02, 0xf5, + 0x21, 0x2d, 0x02, 0xbd, 0xc4, 0xf1, 0xd7, 0x00, + 0x04, 0xbd, 0xe4, 0x98, 0xdf, 0x00, 0xf0, 0x97, + 0x00, 0xf1, 0x93, 0x00, 0x80, 0xb6, 0xd0, 0x04, + 0xff, 0xe9, 0x95, 0xb8, 0xf9, 0x06, 0xf5, 0x1b, + 0x7d, 0x00, 0xb6, 0xe0, 0x04, 0xb6, 0xc0, 0x01, + 0xb1, 0xc6, 0x40, 0x00, 0xf4, 0x1b, 0xdf, 0xf1, + 0xf7, 0x00, 0x04, 0xbd, 0x94, 0x80, 0xf9, 0x00, + 0xb6, 0xf0, 0x04, 0xf1, 0x97, 0x00, 0x05, 0xb8, + 0xf9, 0x06, 0xf4, 0x1b, 0xf1, 0xf0, 0x97, 0x02, + 0xb0, 0x91, 0x00, 0xf0, 0x97, 0x01, 0xf0, 0xc7, + 0x06, 0xb0, 0x91, 0x01, 0xf1, 0xd7, 0x00, 0x04, + 0xf0, 0x97, 0x02, 0xbd, 0xe4, 0x92, 0x0b, 0x00, + 0xbd, 0xa4, 0xb0, 0x91, 0x02, 0xf5, 0x21, 0x2d, + 0x02, 0xbd, 0xc4, 0xf1, 0xd7, 0x00, 0x04, 0xbd, + 0xe4, 0x98, 0xdf, 0x00, 0xf0, 0x97, 0x00, 0xf1, + 0x93, 0x00, 0x80, 0xb6, 0xd0, 0x04, 0xff, 0xe9, + 0x95, 0xb8, 0xf9, 0x06, 0xf4, 0x1b, 0x17, 0xb6, + 0xe0, 0x04, 0xb6, 0xc0, 0x01, 0xb1, 0xc6, 0x40, + 0x00, 0xf4, 0x1b, 0xe0, 0xf1, 0xa7, 0x00, 0x10, + 0xf4, 0x0e, 0x07, 0xf1, 0xa7, 0x00, 0x20, 0xf4, + 0x30, 0x0c, 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x00, + 0xf1, 0xf7, 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0xf9, + 0x10, 0x92, 0xe0, 0x00, 0xf0, 0x97, 0x10, 0xfa, + 0xf9, 0x00, 0xb0, 0xa6, 0x02, 0xf0, 0x1c, 0x0b, + 0xb0, 0xb6, 0x03, 0xf4, 0x0b, 0x0f, 0xb0, 0xb6, + 0x05, 0xf4, 0x0b, 0x09, 0xb0, 0xb6, 0x06, 0xf4, + 0x1b, 0x31, 0xf1, 0x97, 0x80, 0x01, 0x98, 0x99, + 0x00, 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x50, 0xf1, + 0xe7, 0x00, 0xc4, 0xf0, 0xe3, 0x01, 0xb6, 0x94, + 0x0f, 0xbb, 0x9f, 0x00, 0xf0, 0xf7, 0xff, 0xf1, + 0xf3, 0xff, 0x03, 0xfd, 0x9f, 0x04, 0xfa, 0xe9, + 0x00, 0xf0, 0xa7, 0x01, 0xf5, 0x0e, 0x66, 0x00, + 0xb0, 0xb6, 0x04, 0xf4, 0x0b, 0x0f, 0xb0, 0xb6, + 0x07, 0xf4, 0x0b, 0x09, 0xbd, 0xa4, 0xf5, 0x0e, + 0x54, 0x00, 0xf1, 0x97, 0x80, 0x01, 0x98, 0x99, + 0x00, 0xf1, 0xf7, 0x00, 0x40, 0xf0, 0xf3, 0x50, + 0xf1, 0xe7, 0x00, 0xc4, 0xf0, 0xe3, 0x01, 0xb6, + 0x94, 0x0f, 0xbb, 0x9f, 0x00, 0xf0, 0xf7, 0xff, + 0xf1, 0xf3, 0xff, 0x03, 0xfd, 0x9f, 0x04, 0xfa, + 0xe9, 0x00, 0xf1, 0xf7, 0x00, 0xc6, 0xf0, 0xf3, + 0x01, 0xf1, 0x97, 0x00, 0x08, 0xfa, 0xf9, 0x00, + 0xf1, 0x97, 0x84, 0x01, 0x98, 0x9e, 0x00, 0xb7, + 0xf0, 0x00, 0x01, 0xf0, 0x97, 0x01, 0xbb, 0x9e, + 0x04, 0xb6, 0x92, 0x01, 0xfa, 0xf9, 0x00, 0xf0, + 0xa7, 0x03, 0xb0, 0xb6, 0x0b, 0xf4, 0x1b, 0x1d, + 0xf1, 0x97, 0x80, 0x01, 0x98, 0x99, 0x00, 0xf0, + 0xf7, 0x00, 0xf1, 0xe7, 0x00, 0xc4, 0xf0, 0xe3, + 0x01, 0xf0, 0xf3, 0x18, 0xb6, 0x94, 0x0c, 0xf4, + 0x0e, 0x21, 0xb0, 0xb6, 0x0c, 0xf4, 0x1b, 0x2e, + 0xf1, 0x97, 0x80, 0x01, 0x98, 0x99, 0x00, 0xf1, + 0xf7, 0x00, 0x80, 0xf1, 0xe7, 0x00, 0xc4, 0xf0, + 0xe3, 0x01, 0xf0, 0xf3, 0x1b, 0xb6, 0x94, 0x09, + 0xbb, 0x9f, 0x00, 0xf0, 0xf7, 0xff, 0xf1, 0xf3, + 0xff, 0x03, 0xfd, 0x9f, 0x04, 0xfa, 0xe9, 0x00, + 0xf0, 0xa7, 0x01, 0x92, 0xc9, 0x01, 0xb0, 0x96, + 0x01, 0xf4, 0x0c, 0x17, 0x94, 0x19, 0x10, 0xf1, + 0xf7, 0x00, 0x10, 0xf0, 0xf3, 0x02, 0xfd, 0x9f, + 0x05, 0xb7, 0xf2, 0x00, 0x4b, 0xfa, 0xf9, 0x00, + 0xbd, 0xe4, 0xbd, 0xb4, 0xf4, 0x0e, 0x32, 0x98, + 0xdf, 0x00, 0xf4, 0x0e, 0x10, 0xf1, 0x97, 0x00, + 0xc5, 0xf0, 0x93, 0x01, 0xff, 0x9e, 0x9f, 0xc4, + 0x9e, 0x1f, 0xb0, 0xe6, 0x00, 0xf4, 0x0b, 0xf0, + 0xfd, 0xfa, 0x05, 0xf1, 0x97, 0x00, 0xc8, 0xf0, + 0x93, 0x01, 0xfa, 0x9f, 0x00, 0xb6, 0xe2, 0x01, + 0xb6, 0xb0, 0x01, 0xb6, 0xd0, 0x04, 0xb8, 0xb0, + 0x06, 0xf4, 0x1e, 0xce, 0xb0, 0xc6, 0x01, 0xf4, + 0x0b, 0x1b, 0xb0, 0xc6, 0x03, 0xf4, 0x1b, 0x2f, + 0xf4, 0x0e, 0x12, 0xf1, 0x97, 0x00, 0xc5, 0xf0, + 0x93, 0x01, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xc4, + 0x9e, 0x1f, 0xb0, 0xe6, 0x10, 0xf4, 0x1b, 0xee, + 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x01, 0xbd, 0xf4, + 0xff, 0x9f, 0x9f, 0xf0, 0x94, 0x20, 0xf4, 0x0b, + 0x35, 0xf4, 0x0e, 0xef, 0xf1, 0xf7, 0x00, 0x10, + 0xf0, 0xf3, 0x04, 0x94, 0x19, 0x10, 0xfd, 0x9f, + 0x05, 0xf1, 0xf7, 0x00, 0xc5, 0xf0, 0xf3, 0x01, + 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x00, 0xc5, 0xf0, + 0x93, 0x01, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf0, + 0xf7, 0x00, 0xf0, 0xf3, 0x04, 0xfd, 0x9f, 0x04, + 0xf4, 0x1b, 0xeb, 0xf1, 0xf7, 0x00, 0x13, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x10, 0xfa, 0xf9, 0x00, + 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, 0xf1, 0xe7, + 0x00, 0x44, 0xf0, 0xe3, 0x02, 0xf1, 0xc7, 0x00, + 0x43, 0xf0, 0xc3, 0x02, 0xf1, 0xd7, 0x00, 0x42, + 0xf0, 0xd3, 0x02, 0xbd, 0x94, 0xff, 0xe9, 0xff, + 0xb0, 0xf6, 0x00, 0xf4, 0x1d, 0x16, 0x92, 0xa9, + 0x00, 0xfa, 0xda, 0x00, 0xfa, 0xca, 0x00, 0xe3, + 0xff, 0xe6, 0x02, 0xb6, 0x90, 0x01, 0xbc, 0xf9, + 0xa0, 0xb6, 0xd0, 0x04, 0xb6, 0xc0, 0x04, 0xb6, + 0xe0, 0x04, 0xf1, 0x97, 0x20, 0x44, 0xf0, 0x93, + 0x02, 0xb8, 0xe9, 0x06, 0xf4, 0x1b, 0xcf, 0xf8, + 0x00, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, 0xf3, 0x02, + 0xf1, 0x97, 0x00, 0x40, 0xfa, 0xf9, 0x00, 0xf0, + 0x97, 0x00, 0xf0, 0x93, 0x01, 0xbd, 0xf4, 0xff, + 0x9f, 0x9f, 0xf0, 0x94, 0x04, 0xf4, 0x1b, 0xf2, + 0xf1, 0xf7, 0x00, 0x13, 0xf0, 0xf3, 0x02, 0xf1, + 0x97, 0x00, 0x40, 0xfa, 0xf9, 0x00, 0xf8, 0x00, + 0xf1, 0xf7, 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0xf1, + 0x97, 0x00, 0x80, 0xf0, 0x93, 0x00, 0xfa, 0xf9, + 0x00, 0xf1, 0x97, 0xfc, 0x47, 0xf0, 0x93, 0x02, + 0xfa, 0x9a, 0x00, 0xf0, 0x97, 0x01, 0xb7, 0xf0, + 0xfc, 0x3f, 0xfa, 0xf9, 0x00, 0xf5, 0x21, 0x11, + 0x0a, 0xf1, 0xf7, 0xfc, 0x46, 0xf0, 0xf3, 0x02, + 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x05, + 0xb7, 0xf0, 0x00, 0x04, 0xfa, 0xf9, 0x00, 0xf5, + 0x21, 0x11, 0x0a, 0xf1, 0xf7, 0x00, 0x13, 0xf0, + 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x80, 0xf0, 0x93, + 0x00, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf1, 0xf7, + 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, + 0x20, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0xfc, 0x47, + 0xf0, 0x93, 0x02, 0xfa, 0x9a, 0x00, 0xf0, 0x97, + 0x01, 0xb7, 0xf0, 0xfc, 0x3f, 0xfa, 0xf9, 0x00, + 0xf5, 0x21, 0x11, 0x0a, 0xf1, 0xf7, 0xfc, 0x46, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0xff, 0xfa, 0xf9, + 0x00, 0xf0, 0x97, 0x02, 0xb7, 0xf0, 0x00, 0x04, + 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x20, 0xb7, + 0xf2, 0xfc, 0x37, 0xfa, 0xf9, 0x00, 0xf8, 0x00, + 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x02, 0xf9, 0x10, + 0xbd, 0xf4, 0xff, 0x9f, 0x1f, 0xc4, 0x19, 0x04, + 0xf4, 0x0b, 0x1f, 0xf1, 0xa7, 0x00, 0x1a, 0xff, + 0xaf, 0xaf, 0xf1, 0xb7, 0x00, 0x19, 0xff, 0xbf, + 0xbf, 0xf5, 0x21, 0x1c, 0x06, 0xf1, 0xf7, 0x00, + 0x1d, 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, 0x95, + 0x10, 0x08, 0xc4, 0x09, 0xff, 0xc4, 0x0f, 0x40, + 0xb0, 0x96, 0x00, 0xf5, 0x0b, 0x4c, 0x00, 0xb0, + 0xf6, 0x00, 0xf4, 0x0b, 0x16, 0xf1, 0xa7, 0x1c, + 0x9c, 0xf0, 0xa3, 0x40, 0xf0, 0xb7, 0x00, 0xf0, + 0xb3, 0x01, 0xbd, 0xc4, 0xf5, 0x21, 0x00, 0x02, + 0xf1, 0xa7, 0x1c, 0x9c, 0xf0, 0xa3, 0x40, 0xc4, + 0x09, 0x20, 0xf4, 0x0b, 0x0f, 0xf0, 0xb7, 0x00, + 0xf0, 0xb3, 0x08, 0xbd, 0xc4, 0xf5, 0x21, 0x00, + 0x02, 0xf1, 0xa7, 0x9c, 0xa6, 0xf0, 0xa3, 0x41, + 0xc4, 0x09, 0x10, 0xf4, 0x0b, 0x0c, 0xf0, 0xb7, + 0x01, 0xbd, 0xc4, 0xf5, 0x21, 0x00, 0x02, 0xf1, + 0x97, 0x00, 0x01, 0xfa, 0x91, 0x00, 0xfc, 0x10, + 0xfc, 0x00, 0xf8, 0x00, 0xbd, 0x94, 0xff, 0xa9, + 0xef, 0xf0, 0x97, 0xff, 0xfa, 0xb9, 0x00, 0xbd, + 0x94, 0xff, 0xa9, 0xff, 0xb0, 0xf6, 0x00, 0xf5, + 0x1b, 0x69, 0x00, 0xf1, 0x97, 0x55, 0x55, 0xf1, + 0x93, 0x55, 0x55, 0xfa, 0xc9, 0x00, 0xbd, 0x94, + 0xff, 0xa9, 0x9f, 0xf1, 0xf7, 0x55, 0x55, 0xf1, + 0xf3, 0x55, 0x55, 0xb8, 0x9f, 0x06, 0xf5, 0x1b, + 0x4a, 0x00, 0xbd, 0x94, 0xfa, 0xb9, 0x00, 0xff, + 0xa9, 0x9f, 0xb8, 0x9f, 0x06, 0xf4, 0x1b, 0x3b, + 0xf1, 0x97, 0xaa, 0xaa, 0xf1, 0x93, 0xaa, 0xaa, + 0xfa, 0xa9, 0x00, 0xbd, 0x94, 0xff, 0xa9, 0x9f, + 0xf1, 0xf7, 0xaa, 0xaa, 0xf1, 0xf3, 0xaa, 0xaa, + 0xb8, 0x9f, 0x06, 0xf4, 0x1b, 0x1d, 0xf0, 0x97, + 0xff, 0xfa, 0xb9, 0x00, 0xbd, 0x94, 0xff, 0xa9, + 0x9f, 0xb0, 0x96, 0x00, 0xf4, 0x1b, 0x0c, 0xfa, + 0xae, 0x00, 0xf1, 0xa7, 0x00, 0x10, 0xf8, 0x00, + 0xfa, 0xae, 0x00, 0xf1, 0xa7, 0x00, 0x20, 0xf8, + 0x00, 0xf9, 0x00, 0xf0, 0x07, 0x00, 0xf0, 0x03, + 0x02, 0xf9, 0x10, 0xa0, 0x0b, 0x00, 0x10, 0xa0, + 0x0c, 0x00, 0x08, 0x92, 0x0a, 0x00, 0xf1, 0x17, + 0x1c, 0x00, 0xf5, 0x21, 0x74, 0x0b, 0x80, 0x1a, + 0x00, 0xb1, 0xa6, 0x00, 0x20, 0xf4, 0x0b, 0x17, + 0xf1, 0x97, 0x00, 0x07, 0xf0, 0x93, 0x02, 0xb8, + 0x09, 0x06, 0xf4, 0x0b, 0x32, 0xb7, 0x00, 0x00, + 0x01, 0xf4, 0x0e, 0xd2, 0xf0, 0x97, 0x00, 0xf0, + 0x93, 0x02, 0xfa, 0x9a, 0x00, 0xf1, 0x97, 0x80, + 0x01, 0x98, 0x99, 0x00, 0xf1, 0xa7, 0x18, 0x94, + 0xf0, 0xa3, 0x40, 0xbd, 0xc4, 0xf0, 0xb7, 0x01, + 0xbd, 0xd4, 0xbb, 0xb9, 0x04, 0xf5, 0x21, 0x0a, + 0x04, 0xf4, 0x0e, 0x31, 0xf5, 0x21, 0xe2, 0x06, + 0xf1, 0xf7, 0x80, 0x01, 0x80, 0x1a, 0x00, 0xf1, + 0xe7, 0x0a, 0x04, 0xf0, 0x97, 0x00, 0xf0, 0x93, + 0x02, 0xfa, 0x9a, 0x00, 0x98, 0xf9, 0x00, 0xf0, + 0xb7, 0x01, 0xf1, 0xa7, 0x18, 0x94, 0xf0, 0xa3, + 0x40, 0xbd, 0xc4, 0xbb, 0xb9, 0x04, 0xbd, 0xd4, + 0xf9, 0xe5, 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, + 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, 0xf3, + 0x02, 0xf9, 0x10, 0xf1, 0x97, 0x00, 0x10, 0xf9, + 0x20, 0x92, 0xa2, 0x00, 0xf9, 0x30, 0x92, 0xb3, + 0x00, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x0c, 0xb7, + 0xf0, 0xfc, 0x3f, 0xfa, 0xf9, 0x00, 0xf1, 0x07, + 0x11, 0x0a, 0xf9, 0x05, 0xbd, 0xb4, 0xf0, 0xa7, + 0x0f, 0xf1, 0x17, 0x49, 0x01, 0xf9, 0x15, 0xf9, + 0x05, 0xf0, 0xb7, 0x01, 0x92, 0x3a, 0x00, 0xf9, + 0x15, 0xf9, 0x05, 0xbd, 0xa4, 0xf5, 0x21, 0x96, + 0x0a, 0xf9, 0x05, 0xf0, 0xa7, 0x0f, 0xbd, 0xb4, + 0xf9, 0x15, 0xf9, 0x05, 0xf0, 0xa7, 0x03, 0xf0, + 0xb7, 0x01, 0xf9, 0x15, 0xf9, 0x05, 0xf1, 0xf7, + 0xfc, 0x4a, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x0d, + 0xfa, 0xf9, 0x00, 0xf5, 0x21, 0x11, 0x0a, 0xbd, + 0xa4, 0xf1, 0xc7, 0x00, 0x44, 0xf0, 0xc3, 0x02, + 0xf1, 0xb7, 0xa4, 0x00, 0xf0, 0x17, 0x18, 0xf0, + 0x07, 0x14, 0xbd, 0x94, 0xff, 0xc9, 0xdf, 0xb0, + 0xd6, 0x00, 0xf5, 0x1d, 0x5b, 0x00, 0x97, 0xb9, + 0x02, 0x94, 0x9e, 0x02, 0xf1, 0x97, 0x00, 0x03, + 0xf1, 0xf7, 0x00, 0x03, 0xbb, 0xe9, 0x00, 0xb6, + 0xd4, 0x02, 0x97, 0x09, 0x02, 0xb6, 0x94, 0x02, + 0xbb, 0x9f, 0x00, 0xb0, 0x36, 0x08, 0xf4, 0x1b, + 0x12, 0x90, 0xb9, 0x04, 0x80, 0xe2, 0x00, 0xb6, + 0x97, 0x02, 0xb6, 0x94, 0x02, 0xf4, 0x0e, 0x10, + 0x80, 0x92, 0x00, 0xf1, 0xf7, 0x00, 0x03, 0x97, + 0x19, 0x02, 0xb6, 0x94, 0x02, 0xbb, 0x9f, 0x00, + 0x90, 0x2f, 0x01, 0x80, 0x9d, 0x00, 0x97, 0xd9, + 0x08, 0xbc, 0x9f, 0x20, 0xb6, 0x90, 0x01, 0xb6, + 0x94, 0x08, 0xbb, 0xa9, 0x00, 0xb6, 0xb0, 0x08, + 0xb6, 0x00, 0x08, 0xb6, 0x10, 0x08, 0xb6, 0xc0, + 0x04, 0xf1, 0x97, 0x20, 0x44, 0xf0, 0x93, 0x02, + 0xb8, 0xc9, 0x06, 0xf5, 0x1b, 0x87, 0xff, 0xf1, + 0xf7, 0x00, 0x13, 0xf0, 0xf3, 0x02, 0xf1, 0x97, + 0x00, 0x10, 0xfa, 0xf9, 0x00, 0xfc, 0x30, 0xfc, + 0x20, 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, + 0xf9, 0x10, 0xf1, 0x97, 0x00, 0x04, 0xfa, 0xf9, + 0x00, 0xf0, 0xa7, 0x05, 0xf5, 0x21, 0xab, 0x00, + 0xf1, 0x17, 0x4c, 0x01, 0xf1, 0xc7, 0x50, 0x01, + 0x98, 0x19, 0x00, 0x98, 0xcf, 0x00, 0xf1, 0xe7, + 0x00, 0x20, 0xf0, 0xe3, 0x02, 0xbd, 0xd4, 0xbb, + 0x9a, 0x00, 0xbb, 0xfa, 0x00, 0x80, 0x19, 0x00, + 0x80, 0xcf, 0x00, 0xff, 0xed, 0xef, 0xf1, 0x07, + 0x00, 0x03, 0xf0, 0xb7, 0x08, 0x80, 0x0e, 0x25, + 0xbd, 0xa4, 0xf5, 0x21, 0x90, 0x0c, 0x98, 0x1f, + 0x00, 0x98, 0x09, 0x27, 0xf0, 0xe7, 0x00, 0xf0, + 0xe3, 0x02, 0xbb, 0xaf, 0x00, 0xbb, 0x9a, 0x00, + 0x80, 0x1a, 0x00, 0x80, 0x09, 0x27, 0xfa, 0xea, + 0x00, 0xf0, 0xb7, 0x03, 0xbd, 0xa4, 0xf5, 0x21, + 0x90, 0x0c, 0xf1, 0x97, 0x80, 0x01, 0x98, 0x99, + 0x00, 0xf1, 0xa7, 0x18, 0x94, 0xf0, 0xa3, 0x40, + 0xbd, 0xc4, 0xbd, 0xd4, 0xf0, 0xb7, 0x01, 0xbb, + 0xb9, 0x04, 0xf5, 0x21, 0x0a, 0x04, 0xf1, 0xf7, + 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, + 0x04, 0xfa, 0xf9, 0x00, 0xfc, 0x10, 0xfc, 0x00, + 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x0a, + 0xf0, 0xf3, 0x02, 0xf9, 0x10, 0xf1, 0x97, 0x00, + 0x02, 0xfa, 0xf9, 0x00, 0xf1, 0x17, 0x44, 0x01, + 0xf0, 0xa7, 0x03, 0xf5, 0x21, 0xab, 0x00, 0x98, + 0x1f, 0x00, 0xf1, 0xd7, 0x48, 0x01, 0xf1, 0x97, + 0x84, 0x01, 0x98, 0xde, 0x00, 0x98, 0x99, 0x00, + 0xbb, 0xfa, 0x00, 0xf1, 0x07, 0x00, 0x03, 0x80, + 0x1f, 0x00, 0x80, 0x09, 0x3e, 0xbb, 0xea, 0x00, + 0xf1, 0x97, 0x00, 0x20, 0xf0, 0x93, 0x02, 0x80, + 0xde, 0x00, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf0, + 0xb7, 0x03, 0x80, 0x09, 0x01, 0xbd, 0xa4, 0xf5, + 0x21, 0x90, 0x0c, 0x98, 0x1f, 0x00, 0x98, 0x09, + 0x00, 0xf0, 0xe7, 0x00, 0xf0, 0xe3, 0x02, 0xbb, + 0xaf, 0x00, 0xbb, 0x9a, 0x00, 0x80, 0x1a, 0x00, + 0x80, 0x09, 0x00, 0xfa, 0xea, 0x00, 0xf1, 0x97, + 0x80, 0x01, 0x98, 0x99, 0x00, 0xf1, 0xa7, 0x18, + 0x94, 0xf0, 0xa3, 0x40, 0xbd, 0xc4, 0xbd, 0xd4, + 0xf0, 0xb7, 0x01, 0xbb, 0xb9, 0x04, 0xf5, 0x21, + 0x0a, 0x04, 0xf1, 0xf7, 0x00, 0x12, 0xf0, 0xf3, + 0x02, 0xf1, 0x97, 0x00, 0x02, 0xfa, 0xf9, 0x00, + 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x00, + 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0xf9, + 0x10, 0xf1, 0x97, 0x00, 0x01, 0xfa, 0xf9, 0x00, + 0xf0, 0x97, 0x10, 0xb7, 0xf0, 0x00, 0x11, 0xfa, + 0xf9, 0x00, 0xf0, 0x97, 0x0c, 0xb7, 0xf0, 0xfc, + 0x2f, 0xfa, 0xf9, 0x00, 0xf1, 0x07, 0x11, 0x0a, + 0xf9, 0x05, 0xbd, 0xa4, 0xf5, 0x21, 0x96, 0x0a, + 0xf9, 0x05, 0xf0, 0xb7, 0x01, 0xf0, 0xa7, 0x0f, + 0xf1, 0x17, 0x49, 0x01, 0xf9, 0x15, 0xf9, 0x05, + 0xbd, 0xa4, 0xf5, 0x21, 0x40, 0x0a, 0xf9, 0x05, + 0xf0, 0xa7, 0x0f, 0xbd, 0xb4, 0xf9, 0x15, 0xf9, + 0x05, 0xf0, 0xa7, 0x03, 0xf0, 0xb7, 0x01, 0xf9, + 0x15, 0xf9, 0x05, 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x0d, 0xfa, 0xf9, 0x00, + 0xf0, 0xa7, 0x08, 0xf5, 0x21, 0x7c, 0x04, 0xf1, + 0xf7, 0x00, 0x1b, 0xf0, 0xf3, 0x02, 0xbd, 0x94, + 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x80, 0x01, 0x98, + 0x99, 0x00, 0xf1, 0xa7, 0x18, 0x94, 0xf0, 0xa3, + 0x40, 0xbd, 0xc4, 0xbd, 0xd4, 0xf0, 0xb7, 0x01, + 0xbb, 0xb9, 0x04, 0xf5, 0x21, 0x0a, 0x04, 0xf1, + 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf1, 0x97, + 0x00, 0x01, 0xfa, 0xf9, 0x00, 0xfc, 0x10, 0xfc, + 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, 0x00, + 0x0a, 0xf0, 0xf3, 0x02, 0xf9, 0x10, 0xf0, 0x97, + 0x00, 0xf0, 0x93, 0x08, 0xf9, 0x20, 0xfa, 0xf9, + 0x00, 0xf1, 0x97, 0x5c, 0x01, 0x98, 0x9a, 0x00, + 0xf5, 0x21, 0xcb, 0x06, 0xf1, 0x97, 0x78, 0x01, + 0x98, 0x99, 0x00, 0xb6, 0x92, 0x01, 0xb0, 0x96, + 0x01, 0xf4, 0x0c, 0x0a, 0xf0, 0xa7, 0x08, 0xf5, + 0x21, 0x75, 0x01, 0xf1, 0xf7, 0x00, 0x1d, 0xf0, + 0xf3, 0x02, 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xf0, + 0x97, 0x0b, 0xb7, 0xf0, 0x00, 0x01, 0xfa, 0xf9, + 0x00, 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x04, 0x02, + 0xb7, 0xf0, 0x00, 0x0c, 0xfa, 0xf9, 0x00, 0xf0, + 0x97, 0x10, 0xb7, 0xf2, 0x00, 0x0f, 0xfa, 0xf9, + 0x00, 0xf0, 0xa7, 0x02, 0xf5, 0x21, 0x34, 0x03, + 0xf1, 0x97, 0x00, 0x03, 0x98, 0x9f, 0x3f, 0xf1, + 0x97, 0xab, 0xec, 0xf1, 0x93, 0x0b, 0xad, 0xb8, + 0xf9, 0x06, 0xf5, 0x1b, 0x23, 0x03, 0xf1, 0x97, + 0x18, 0x00, 0x98, 0x9a, 0x00, 0xf5, 0x21, 0xda, + 0x01, 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, 0x02, + 0xf0, 0x97, 0x0c, 0xfa, 0xf9, 0x00, 0xf5, 0x21, + 0x11, 0x0a, 0xf1, 0xf7, 0xfc, 0x47, 0xf0, 0xf3, + 0x02, 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xf0, 0x97, + 0x04, 0xb7, 0xf0, 0x00, 0x03, 0xfa, 0xf9, 0x00, + 0xf1, 0x97, 0x84, 0x01, 0x98, 0x9f, 0x00, 0xf1, + 0xd7, 0x00, 0xd3, 0xf0, 0xd3, 0x01, 0x94, 0xfe, + 0x03, 0x94, 0xf9, 0x06, 0xbb, 0x9e, 0x02, 0xbb, + 0x9f, 0x02, 0xb6, 0x90, 0x40, 0xfa, 0xd9, 0x00, + 0xf1, 0x97, 0x00, 0x03, 0x98, 0x99, 0x03, 0xf1, + 0xf7, 0x00, 0xc1, 0xf0, 0xf3, 0x01, 0xf1, 0x94, + 0xff, 0xff, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0xc8, + 0x00, 0x98, 0x9e, 0x00, 0xf1, 0x07, 0xe6, 0x07, + 0xf0, 0xa7, 0x02, 0xf0, 0xb7, 0x04, 0xf0, 0xc7, + 0x01, 0xf1, 0xd7, 0x84, 0x00, 0xf9, 0x05, 0xf1, + 0x97, 0x80, 0x00, 0x98, 0x9e, 0x00, 0xf0, 0xa7, + 0x02, 0xf0, 0xb7, 0x03, 0xf0, 0xc7, 0x04, 0xf1, + 0xd7, 0x20, 0x00, 0xf9, 0x05, 0xf5, 0x21, 0x11, + 0x0a, 0xf1, 0x97, 0x78, 0x01, 0x98, 0x99, 0x00, + 0xb0, 0x96, 0x02, 0xf5, 0x1b, 0x50, 0x01, 0xf1, + 0x97, 0x70, 0x01, 0x98, 0x9a, 0x00, 0xf5, 0x21, + 0xcb, 0x06, 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x0c, 0xfa, 0xf9, 0x00, 0xf1, + 0x07, 0x11, 0x0a, 0xf9, 0x05, 0xf0, 0xa7, 0x0f, + 0xbd, 0xb4, 0xf1, 0x17, 0x49, 0x01, 0xf9, 0x15, + 0xf9, 0x05, 0xf0, 0xb7, 0x01, 0xf0, 0xa7, 0x08, + 0xf9, 0x15, 0xf9, 0x05, 0xbd, 0xa4, 0xf5, 0x21, + 0x96, 0x0a, 0xf1, 0x97, 0x00, 0x03, 0x98, 0x9b, + 0x25, 0x98, 0x99, 0x28, 0xbd, 0xc4, 0xf1, 0xd7, + 0xa4, 0x00, 0xf1, 0xe7, 0x00, 0x43, 0xf0, 0xe3, + 0x02, 0xc7, 0x9f, 0xf0, 0xf1, 0x94, 0xff, 0xff, + 0xbc, 0x9f, 0xf0, 0xf4, 0x0e, 0x15, 0x98, 0x99, + 0x00, 0xbc, 0xf9, 0x90, 0xfa, 0xe9, 0x00, 0xb6, + 0xc0, 0x01, 0xb6, 0xd0, 0x08, 0xb6, 0xe0, 0x04, + 0x97, 0xd9, 0x02, 0xf1, 0xa7, 0x00, 0x03, 0xb6, + 0x94, 0x02, 0xbb, 0x9a, 0x00, 0xb8, 0xcb, 0x06, + 0xf4, 0x1b, 0xde, 0xf5, 0x21, 0x11, 0x0a, 0xf1, + 0xf7, 0xfc, 0x47, 0xf0, 0xf3, 0x02, 0xbd, 0x94, + 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x04, 0xb7, 0xf0, + 0x00, 0x03, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x38, + 0xb7, 0xf2, 0xfc, 0x77, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0x00, 0x03, 0x98, 0x99, 0x28, 0xb7, 0xf2, + 0x00, 0x12, 0xf1, 0x94, 0xff, 0xff, 0xfa, 0xf9, + 0x00, 0xf1, 0x97, 0xec, 0x00, 0x98, 0x9e, 0x00, + 0xf1, 0xd7, 0xcc, 0x00, 0xf0, 0xa7, 0x02, 0xf0, + 0xb7, 0x05, 0x92, 0xac, 0x00, 0xf1, 0x07, 0x11, + 0x0a, 0xf5, 0x21, 0xe6, 0x07, 0xf9, 0x05, 0xf0, + 0xa7, 0x0f, 0xbd, 0xb4, 0xf1, 0x17, 0x49, 0x01, + 0xf9, 0x15, 0xf9, 0x05, 0xf0, 0xb7, 0x01, 0xf0, + 0xa7, 0x03, 0xf9, 0x15, 0xf9, 0x05, 0xbd, 0xa4, + 0xf5, 0x21, 0x96, 0x0a, 0xf1, 0x97, 0x00, 0x03, + 0x98, 0x9b, 0x01, 0x98, 0x99, 0x03, 0xbd, 0xc4, + 0xf0, 0xd7, 0x14, 0xf1, 0xe7, 0x00, 0x43, 0xf0, + 0xe3, 0x02, 0xc7, 0x9f, 0xf0, 0xf1, 0x94, 0xff, + 0xff, 0xbc, 0x9f, 0xf0, 0xf4, 0x0e, 0x15, 0x98, + 0x99, 0x00, 0xbc, 0xf9, 0x90, 0xfa, 0xe9, 0x00, + 0xb6, 0xc0, 0x01, 0xb6, 0xd0, 0x08, 0xb6, 0xe0, + 0x04, 0x97, 0xd9, 0x02, 0xf1, 0xa7, 0x00, 0x03, + 0xb6, 0x94, 0x02, 0xbb, 0x9a, 0x00, 0xb8, 0xcb, + 0x06, 0xf4, 0x1b, 0xde, 0xf5, 0x21, 0x11, 0x0a, + 0xf1, 0x97, 0x5c, 0x01, 0x98, 0x9a, 0x00, 0xf5, + 0x21, 0xcb, 0x06, 0xf1, 0x97, 0x7c, 0x01, 0x98, + 0x99, 0x00, 0xb0, 0x96, 0x01, 0xf5, 0x1b, 0x9f, + 0x00, 0xf1, 0x97, 0x74, 0x01, 0x98, 0x9a, 0x00, + 0xf5, 0x21, 0xcb, 0x06, 0xf1, 0x97, 0x84, 0x01, + 0x98, 0x99, 0x00, 0xf1, 0xf7, 0x00, 0xd3, 0xf0, + 0xf3, 0x01, 0xb6, 0x94, 0x02, 0xb6, 0x90, 0x3f, + 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x03, 0x98, + 0x99, 0x3a, 0xb7, 0xf2, 0x00, 0x12, 0xf1, 0x94, + 0xff, 0xff, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x24, + 0x01, 0x98, 0x9e, 0x00, 0xf1, 0x07, 0xe6, 0x07, + 0xf0, 0xa7, 0x02, 0xf0, 0xb7, 0x07, 0xf0, 0xc7, + 0x01, 0xf1, 0xd7, 0x14, 0x01, 0xf9, 0x05, 0xf1, + 0x97, 0x10, 0x01, 0x98, 0x9e, 0x00, 0xf0, 0xa7, + 0x02, 0xf0, 0xb7, 0x06, 0xf0, 0xc7, 0x03, 0xf1, + 0xd7, 0xf0, 0x00, 0xf9, 0x05, 0xf1, 0x97, 0x30, + 0x01, 0x98, 0x9e, 0x00, 0xf0, 0xa7, 0x02, 0xf0, + 0xb7, 0x0b, 0xf0, 0xc7, 0x03, 0xf1, 0xd7, 0x28, + 0x01, 0xf9, 0x05, 0xf1, 0x97, 0x38, 0x01, 0x98, + 0x9e, 0x00, 0xf0, 0xa7, 0x02, 0xf0, 0xb7, 0x0c, + 0xf0, 0xc7, 0x04, 0xf1, 0xd7, 0x34, 0x01, 0xf9, + 0x05, 0xf1, 0x97, 0x5c, 0x01, 0x98, 0x9a, 0x00, + 0xf5, 0x21, 0xcb, 0x06, 0xf1, 0xf7, 0xfc, 0x4a, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x0d, 0xfa, 0xf9, + 0x00, 0xf5, 0x21, 0x11, 0x0a, 0xf1, 0x97, 0x80, + 0x01, 0x98, 0x99, 0x00, 0xf1, 0xa7, 0x18, 0x94, + 0xf0, 0xa3, 0x40, 0xbd, 0xc4, 0xbd, 0xd4, 0xf0, + 0xb7, 0x01, 0xbb, 0xb9, 0x04, 0xf5, 0x21, 0x0a, + 0x04, 0xf1, 0xf7, 0x00, 0x1d, 0xf0, 0xf3, 0x02, + 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x04, + 0xb7, 0xf0, 0x00, 0x01, 0xfa, 0xf9, 0x00, 0xf0, + 0x97, 0x00, 0xf1, 0x93, 0x00, 0x07, 0xb7, 0xf0, + 0x00, 0x0c, 0xfa, 0xf9, 0x00, 0xf1, 0xf7, 0x00, + 0x0c, 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, 0xf9, + 0x00, 0xb7, 0xf2, 0x00, 0x03, 0xfa, 0xf9, 0x00, + 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x04, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x00, 0xf0, + 0x93, 0x08, 0xb7, 0xf0, 0x00, 0x12, 0xfa, 0xf9, + 0x00, 0xf5, 0x0e, 0x5a, 0x00, 0xf1, 0x07, 0x80, + 0x01, 0xf0, 0xa7, 0x01, 0xf5, 0x21, 0x6d, 0x05, + 0x98, 0x0b, 0x00, 0xf0, 0x17, 0x01, 0xf1, 0x27, + 0x0a, 0x04, 0xf1, 0xa7, 0x34, 0x98, 0xf0, 0xa3, + 0x40, 0xbc, 0x1b, 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, + 0xf9, 0x25, 0x98, 0x0b, 0x00, 0xf1, 0xa7, 0x18, + 0x94, 0xf0, 0xa3, 0x40, 0xbd, 0xc4, 0xbd, 0xd4, + 0xbc, 0x1b, 0xb4, 0xf9, 0x25, 0xf1, 0xf7, 0x00, + 0x09, 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, + 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x08, 0xfa, 0xf9, + 0x00, 0xbd, 0xa4, 0xfc, 0x20, 0xfc, 0x10, 0xfc, + 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, 0x00, + 0x0a, 0xf0, 0xf3, 0x02, 0xf9, 0x10, 0xf0, 0x97, + 0x00, 0xf0, 0x93, 0x04, 0xf9, 0x20, 0x92, 0xc2, + 0x00, 0xfa, 0xf9, 0x00, 0xb0, 0xc6, 0x02, 0xf4, + 0x1b, 0x24, 0xb7, 0xf0, 0x00, 0x13, 0xbd, 0x94, + 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x09, 0xb7, 0xf0, + 0x00, 0x01, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x00, + 0xf1, 0x93, 0x03, 0x04, 0xb7, 0xf0, 0x00, 0x0c, + 0xf4, 0x0e, 0x24, 0xf1, 0xf7, 0x00, 0x1d, 0xf0, + 0xf3, 0x02, 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xf0, + 0x97, 0x0a, 0xb7, 0xf0, 0x00, 0x01, 0xfa, 0xf9, + 0x00, 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x02, 0x05, + 0xb7, 0xf0, 0x00, 0x0c, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0x18, 0x00, 0x98, 0x9a, 0x00, 0xf5, 0x21, + 0xda, 0x01, 0xf1, 0x97, 0x5c, 0x01, 0x98, 0x9a, + 0x00, 0xf5, 0x21, 0xcb, 0x06, 0xf1, 0xf7, 0xfc, + 0x4a, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x0c, 0xfa, + 0xf9, 0x00, 0xf5, 0x21, 0x11, 0x0a, 0xf1, 0xf7, + 0xfc, 0x47, 0xf0, 0xf3, 0x02, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf0, 0x97, 0x03, 0xb7, 0xf0, 0x00, + 0x03, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x03, + 0x98, 0x99, 0x03, 0xf1, 0xf7, 0x00, 0xc0, 0xf0, + 0xf3, 0x01, 0xf1, 0x94, 0xff, 0xff, 0xfa, 0xf9, + 0x00, 0xf1, 0x97, 0xc8, 0x00, 0x98, 0x9e, 0x00, + 0xf0, 0xa7, 0x01, 0xf1, 0x07, 0xe6, 0x07, 0x92, + 0xac, 0x00, 0xf0, 0xb7, 0x04, 0xf1, 0xd7, 0x84, + 0x00, 0xf9, 0x05, 0xf1, 0x97, 0x80, 0x00, 0x98, + 0x9e, 0x00, 0xf0, 0xa7, 0x01, 0xf0, 0xb7, 0x03, + 0xf0, 0xc7, 0x04, 0xf1, 0xd7, 0x20, 0x00, 0xf9, + 0x05, 0xf5, 0x21, 0x11, 0x0a, 0xf1, 0x97, 0x78, + 0x01, 0x98, 0x99, 0x00, 0xb0, 0x96, 0x02, 0xf5, + 0x1b, 0x49, 0x01, 0xf1, 0x97, 0x70, 0x01, 0x98, + 0x9a, 0x00, 0xf5, 0x21, 0xcb, 0x06, 0xf1, 0xf7, + 0xfc, 0x4a, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x0c, + 0xfa, 0xf9, 0x00, 0xf1, 0x07, 0x11, 0x0a, 0xf9, + 0x05, 0xf0, 0xa7, 0x0f, 0xbd, 0xb4, 0xf1, 0x17, + 0x49, 0x01, 0xf9, 0x15, 0xf9, 0x05, 0xf0, 0xb7, + 0x01, 0xf0, 0xa7, 0x08, 0xf9, 0x15, 0xf9, 0x05, + 0xbd, 0xa4, 0xf5, 0x21, 0x96, 0x0a, 0xf1, 0x97, + 0x00, 0x03, 0x98, 0x9b, 0x25, 0x98, 0x99, 0x28, + 0xbd, 0xc4, 0xf1, 0xd7, 0xa4, 0x00, 0xf1, 0xe7, + 0x00, 0x42, 0xf0, 0xe3, 0x02, 0xc7, 0x9f, 0xf0, + 0xf1, 0x94, 0xff, 0xff, 0xbc, 0x9f, 0xf0, 0xf4, + 0x0e, 0x15, 0x98, 0x99, 0x00, 0xbc, 0xf9, 0x90, + 0xfa, 0xe9, 0x00, 0xb6, 0xc0, 0x01, 0xb6, 0xd0, + 0x08, 0xb6, 0xe0, 0x04, 0x97, 0xd9, 0x02, 0xf1, + 0xa7, 0x00, 0x03, 0xb6, 0x94, 0x02, 0xbb, 0x9a, + 0x00, 0xb8, 0xcb, 0x06, 0xf4, 0x1b, 0xde, 0xf5, + 0x21, 0x11, 0x0a, 0xf1, 0xf7, 0xfc, 0x47, 0xf0, + 0xf3, 0x02, 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xf0, + 0x97, 0x03, 0xb7, 0xf0, 0x00, 0x03, 0xfa, 0xf9, + 0x00, 0xf1, 0x97, 0x00, 0x03, 0x98, 0x99, 0x28, + 0xf1, 0xf7, 0x00, 0xc0, 0xf0, 0xf3, 0x01, 0xf1, + 0x94, 0xff, 0xff, 0xfa, 0xf9, 0x00, 0xf1, 0x97, + 0xec, 0x00, 0x98, 0x9e, 0x00, 0xf0, 0xc7, 0x02, + 0xf1, 0xd7, 0xcc, 0x00, 0xf0, 0xa7, 0x01, 0xf0, + 0xb7, 0x05, 0xf1, 0x07, 0x11, 0x0a, 0xf5, 0x21, + 0xe6, 0x07, 0xf9, 0x05, 0xf0, 0xa7, 0x0f, 0xbd, + 0xb4, 0xf1, 0x17, 0x49, 0x01, 0xf9, 0x15, 0xf9, + 0x05, 0xf0, 0xb7, 0x01, 0xf0, 0xa7, 0x03, 0xf9, + 0x15, 0xf9, 0x05, 0xbd, 0xa4, 0xf5, 0x21, 0x96, + 0x0a, 0xf1, 0x97, 0x00, 0x03, 0x98, 0x9b, 0x01, + 0x98, 0x99, 0x03, 0xbd, 0xc4, 0xf0, 0xd7, 0x14, + 0xf1, 0xe7, 0x00, 0x42, 0xf0, 0xe3, 0x02, 0xc7, + 0x9f, 0xf0, 0xf1, 0x94, 0xff, 0xff, 0xbc, 0x9f, + 0xf0, 0xf4, 0x0e, 0x15, 0x98, 0x99, 0x00, 0xbc, + 0xf9, 0x90, 0xfa, 0xe9, 0x00, 0xb6, 0xc0, 0x01, + 0xb6, 0xd0, 0x08, 0xb6, 0xe0, 0x04, 0x97, 0xd9, + 0x02, 0xf1, 0xa7, 0x00, 0x03, 0xb6, 0x94, 0x02, + 0xbb, 0x9a, 0x00, 0xb8, 0xcb, 0x06, 0xf4, 0x1b, + 0xde, 0xf5, 0x21, 0x11, 0x0a, 0xf1, 0x97, 0x5c, + 0x01, 0x98, 0x9a, 0x00, 0xf5, 0x21, 0xcb, 0x06, + 0xf1, 0x97, 0x7c, 0x01, 0x98, 0x99, 0x00, 0xb0, + 0x96, 0x01, 0xf5, 0x1b, 0x8b, 0x00, 0xf1, 0x97, + 0x74, 0x01, 0x98, 0x9a, 0x00, 0xf5, 0x21, 0xcb, + 0x06, 0xf1, 0x97, 0x00, 0x03, 0x98, 0x99, 0x3a, + 0xf1, 0xf7, 0x00, 0xc0, 0xf0, 0xf3, 0x01, 0xf1, + 0x94, 0xff, 0xff, 0xfa, 0xf9, 0x00, 0xf1, 0x97, + 0x24, 0x01, 0x98, 0x9e, 0x00, 0xf1, 0x07, 0xe6, + 0x07, 0xf0, 0xa7, 0x01, 0xf0, 0xb7, 0x07, 0x92, + 0xac, 0x00, 0xf1, 0xd7, 0x14, 0x01, 0xf9, 0x05, + 0xf1, 0x97, 0x10, 0x01, 0x98, 0x9e, 0x00, 0xf0, + 0xa7, 0x01, 0xf0, 0xb7, 0x06, 0xf0, 0xc7, 0x03, + 0xf1, 0xd7, 0xf0, 0x00, 0xf9, 0x05, 0xf1, 0x97, + 0x30, 0x01, 0x98, 0x9e, 0x00, 0xf0, 0xa7, 0x01, + 0xf0, 0xb7, 0x0b, 0xf0, 0xc7, 0x03, 0xf1, 0xd7, + 0x28, 0x01, 0xf9, 0x05, 0xf1, 0x97, 0x38, 0x01, + 0x98, 0x9e, 0x00, 0xf0, 0xa7, 0x01, 0xf0, 0xb7, + 0x0c, 0xf0, 0xc7, 0x04, 0xf1, 0xd7, 0x34, 0x01, + 0xf9, 0x05, 0xf1, 0x97, 0x5c, 0x01, 0x98, 0x9a, + 0x00, 0xf5, 0x21, 0xcb, 0x06, 0xf1, 0x97, 0x18, + 0x00, 0x98, 0x9a, 0x00, 0xf5, 0x21, 0xda, 0x01, + 0xf1, 0x97, 0x00, 0x03, 0xf0, 0xa7, 0x02, 0xf1, + 0xf7, 0xab, 0xec, 0xf1, 0xf3, 0x0b, 0xad, 0x80, + 0x9f, 0x3f, 0xf5, 0x21, 0xe9, 0x02, 0xf5, 0x21, + 0x9b, 0x06, 0xf1, 0xf7, 0x00, 0x84, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0x00, 0x84, 0xf0, 0x93, 0x02, 0xbd, 0xf4, + 0xff, 0x9f, 0x9f, 0xb0, 0x96, 0x00, 0xf4, 0x1b, + 0xf1, 0xf1, 0x07, 0x80, 0x01, 0xf1, 0x17, 0x0a, + 0x04, 0xb0, 0x26, 0x00, 0xf5, 0x1b, 0x52, 0x00, + 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x0d, 0xfa, 0xf9, 0x00, 0xf5, 0x21, 0x11, + 0x0a, 0x98, 0x09, 0x00, 0xf1, 0xa7, 0x18, 0x94, + 0xf0, 0xa3, 0x40, 0xbd, 0xc4, 0xbd, 0xd4, 0xf0, + 0xb7, 0x01, 0xbb, 0xb9, 0x04, 0xf9, 0x15, 0xf1, + 0xf7, 0x00, 0x1d, 0xf0, 0xf3, 0x02, 0xbd, 0x94, + 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x04, 0xb7, 0xf0, + 0x00, 0x01, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x00, + 0xf1, 0x93, 0x00, 0x02, 0xb7, 0xf0, 0x00, 0x0c, + 0xfa, 0xf9, 0x00, 0xf4, 0x0e, 0x19, 0x98, 0x09, + 0x00, 0xf0, 0xb7, 0x01, 0xf1, 0xa7, 0x18, 0x94, + 0xf0, 0xa3, 0x40, 0xbd, 0xc4, 0xbb, 0xb9, 0x04, + 0xbd, 0xd4, 0xf9, 0x15, 0xf1, 0xf7, 0x00, 0x0c, + 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, 0xf9, 0x00, + 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x01, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x00, 0xf0, + 0x93, 0x04, 0xb7, 0xf0, 0x00, 0x12, 0xfa, 0xf9, + 0x00, 0xfc, 0x20, 0xfc, 0x10, 0xfc, 0x00, 0xf8, + 0x00, 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x08, 0xfa, 0xf9, 0x00, + 0xf1, 0x07, 0xc8, 0x01, 0xf1, 0x97, 0xcc, 0x01, + 0x98, 0x0f, 0x00, 0x98, 0x99, 0x00, 0xf1, 0xe7, + 0x10, 0x02, 0xf1, 0xc7, 0x14, 0x02, 0xb8, 0x9f, + 0x06, 0xf4, 0x1b, 0x14, 0x98, 0xed, 0x00, 0x98, + 0xc9, 0x00, 0xb8, 0x9d, 0x06, 0xf5, 0x1b, 0x42, + 0x00, 0xf5, 0x0e, 0x00, 0x02, 0x98, 0xed, 0x00, + 0x98, 0xc9, 0x00, 0xb8, 0x9d, 0x06, 0xf4, 0x1b, + 0x31, 0xf1, 0xe7, 0x88, 0x01, 0xc4, 0xf9, 0x07, + 0xb6, 0x94, 0x03, 0xbb, 0x9e, 0x00, 0x98, 0x9e, + 0x00, 0x98, 0x9b, 0x01, 0xb6, 0xf0, 0x01, 0xf1, + 0x97, 0xff, 0x87, 0x80, 0x0f, 0x00, 0xff, 0xe9, + 0xa4, 0xb0, 0xf6, 0x10, 0xf4, 0x1b, 0x3a, 0xbd, + 0xf4, 0x80, 0x0f, 0x00, 0xf4, 0x0e, 0x32, 0xf1, + 0xe7, 0xd0, 0x01, 0xc4, 0xd9, 0x07, 0xb6, 0x94, + 0x03, 0xbb, 0x9e, 0x00, 0x98, 0x9f, 0x00, 0x98, + 0x9b, 0x01, 0xf1, 0x97, 0xff, 0x87, 0xf1, 0xe7, + 0x10, 0x02, 0xff, 0xf9, 0xa4, 0x90, 0xd9, 0x01, + 0x80, 0xe9, 0x00, 0xb0, 0x96, 0x10, 0xf4, 0x1b, + 0x08, 0xbd, 0xf4, 0x80, 0xef, 0x00, 0xb0, 0xa6, + 0x16, 0xf5, 0x0b, 0x20, 0x01, 0xb0, 0xa6, 0x16, + 0xf5, 0x0c, 0x73, 0x00, 0xb0, 0xa6, 0x10, 0xf5, + 0x0b, 0x0a, 0x01, 0xb0, 0xa6, 0x10, 0xf4, 0x0c, + 0x34, 0xb0, 0xa6, 0x02, 0xf5, 0x0b, 0xd7, 0x00, + 0xb0, 0xa6, 0x02, 0xf4, 0x0c, 0x15, 0xb0, 0xa6, + 0x00, 0xf5, 0x0b, 0x68, 0x01, 0xb0, 0xa6, 0x01, + 0xf5, 0x1b, 0x5a, 0x01, 0xf5, 0x0e, 0xb9, 0x00, + 0xb0, 0xa6, 0x06, 0xf5, 0x0b, 0xd6, 0x00, 0xb0, + 0xa6, 0x08, 0xf5, 0x1b, 0x48, 0x01, 0xf5, 0x0e, + 0xb8, 0x00, 0xb0, 0xa6, 0x13, 0xf5, 0x0b, 0xf4, + 0x00, 0xb0, 0xa6, 0x13, 0xf4, 0x0c, 0x15, 0xb0, + 0xa6, 0x11, 0xf5, 0x0b, 0xd7, 0x00, 0xb0, 0xa6, + 0x12, 0xf5, 0x1b, 0x29, 0x01, 0xf5, 0x0e, 0x18, + 0x01, 0xb0, 0xa6, 0x14, 0xf5, 0x0b, 0xfc, 0x00, + 0xb0, 0xa6, 0x15, 0xf5, 0x1b, 0x17, 0x01, 0xf5, + 0x0e, 0x1a, 0x01, 0xb0, 0xa6, 0x26, 0xf5, 0x0b, + 0xd5, 0x00, 0xb0, 0xa6, 0x26, 0xf4, 0x0c, 0x34, + 0xb0, 0xa6, 0x19, 0xf5, 0x0b, 0xcf, 0x00, 0xb0, + 0xa6, 0x19, 0xf4, 0x0c, 0x15, 0xb0, 0xa6, 0x17, + 0xf5, 0x0b, 0xb4, 0x00, 0xb0, 0xa6, 0x18, 0xf5, + 0x1b, 0xeb, 0x00, 0xf5, 0x0e, 0xcc, 0x00, 0xb0, + 0xa6, 0x21, 0xf5, 0x0b, 0x60, 0x00, 0xb0, 0xa6, + 0x25, 0xf5, 0x1b, 0xd9, 0x00, 0xf5, 0x0e, 0x74, + 0x00, 0xb0, 0xa6, 0x29, 0xf5, 0x0b, 0x7d, 0x00, + 0xb0, 0xa6, 0x29, 0xf4, 0x0c, 0x15, 0xb0, 0xa6, + 0x27, 0xf5, 0x0b, 0xad, 0x00, 0xb0, 0xa6, 0x28, + 0xf5, 0x1b, 0xba, 0x00, 0xf5, 0x0e, 0x8d, 0x00, + 0xf0, 0x97, 0x00, 0xf1, 0x93, 0xff, 0xff, 0xbb, + 0xa9, 0x00, 0xb0, 0xa6, 0x01, 0xf5, 0x0c, 0xa5, + 0x00, 0xf5, 0x0e, 0xa8, 0x00, 0xf0, 0xc7, 0x02, + 0xf4, 0x0e, 0x10, 0xf0, 0xc7, 0x01, 0xf5, 0x21, + 0x9b, 0x0f, 0xf5, 0x0e, 0x97, 0x00, 0xbd, 0xc4, + 0xbd, 0xd4, 0xf5, 0x21, 0x9b, 0x13, 0xf5, 0x0e, + 0x8b, 0x00, 0xf1, 0x97, 0x18, 0x00, 0xf4, 0x0e, + 0x37, 0xf5, 0x21, 0xe6, 0x04, 0xf5, 0x0e, 0x7c, + 0x00, 0xf5, 0x21, 0x4a, 0x0e, 0xf5, 0x0e, 0x74, + 0x00, 0xf5, 0x21, 0xa7, 0x0d, 0xf5, 0x0e, 0x6c, + 0x00, 0xf5, 0x21, 0xfc, 0x04, 0xf5, 0x0e, 0x64, + 0x00, 0xf5, 0x21, 0xee, 0x0e, 0xf5, 0x0e, 0x5c, + 0x00, 0xf5, 0x21, 0xf9, 0x0b, 0xf5, 0x0e, 0x54, + 0x00, 0xf1, 0x97, 0x5c, 0x01, 0x80, 0x9b, 0x00, + 0xf5, 0x0e, 0x49, 0x00, 0xf1, 0x97, 0x70, 0x01, + 0xf4, 0x0e, 0xf5, 0xf1, 0x97, 0x74, 0x01, 0xf4, + 0x0e, 0xee, 0xf1, 0x97, 0x78, 0x01, 0xf4, 0x0e, + 0xe7, 0xf1, 0x97, 0x7c, 0x01, 0xf4, 0x0e, 0xe0, + 0xf5, 0x21, 0x82, 0x03, 0xf4, 0x0e, 0x25, 0xf5, + 0x21, 0x71, 0x00, 0xf4, 0x0e, 0x1e, 0xf5, 0x21, + 0x8e, 0x00, 0xf4, 0x0e, 0x17, 0xf1, 0x97, 0x3c, + 0x01, 0xf0, 0xe7, 0x01, 0x80, 0x9e, 0x00, 0xf4, + 0x0e, 0x0a, 0xf0, 0xa7, 0x11, 0xf5, 0x21, 0x97, + 0x05, 0xf1, 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, + 0xf0, 0x97, 0x08, 0xfa, 0xf9, 0x00, 0xfc, 0x00, + 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0x3c, 0x01, 0xbd, 0xf4, 0x80, 0x9f, 0x00, + 0xf1, 0xf7, 0x00, 0x12, 0xf0, 0x97, 0x02, 0xfa, + 0xf9, 0x00, 0xf1, 0x97, 0x13, 0x00, 0xfe, 0x90, + 0x00, 0xf1, 0xf7, 0x00, 0x07, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x04, 0xf1, 0x97, + 0x04, 0x50, 0xfa, 0xf9, 0x00, 0xf1, 0xf7, 0x00, + 0x03, 0xf0, 0x97, 0x04, 0xfa, 0xf9, 0x00, 0xf1, + 0xf7, 0x18, 0x01, 0xf0, 0xf3, 0x01, 0xf1, 0x97, + 0x2d, 0x20, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x2b, + 0x20, 0xb6, 0xf2, 0x04, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0x02, 0x20, 0xb6, 0xf2, 0x04, 0xfa, 0xf9, + 0x00, 0xf4, 0x31, 0x10, 0xf4, 0x31, 0x02, 0xf1, + 0x97, 0x00, 0x86, 0xf0, 0x93, 0x01, 0xbd, 0xe4, + 0xff, 0x9e, 0x9f, 0xf0, 0x94, 0x1f, 0xf1, 0xf7, + 0x80, 0x01, 0x80, 0xf9, 0x00, 0xf1, 0x97, 0x00, + 0x82, 0xf0, 0x93, 0x01, 0xff, 0x9e, 0x9f, 0xf0, + 0x94, 0x1f, 0xf1, 0xf7, 0x84, 0x01, 0x80, 0xf9, + 0x00, 0xf1, 0x97, 0x00, 0xc0, 0xf0, 0x93, 0x01, + 0xfa, 0x9e, 0x00, 0xf1, 0xf7, 0x00, 0xc1, 0xf0, + 0xf3, 0x01, 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0x21, 0x43, 0xf1, 0x93, 0x65, 0x87, 0xb7, + 0xf0, 0x00, 0x3f, 0xfa, 0xf9, 0x00, 0xf4, 0x28, + 0x02, 0xf5, 0x21, 0x51, 0x17, 0xf1, 0x97, 0x3c, + 0x01, 0x98, 0x99, 0x00, 0xb0, 0x96, 0x00, 0xf4, + 0x1b, 0x20, 0xf4, 0x31, 0x02, 0xf1, 0x97, 0xcc, + 0x01, 0x98, 0x9f, 0x00, 0xf1, 0x97, 0xc8, 0x01, + 0x98, 0x99, 0x00, 0xb8, 0xf9, 0x06, 0xf4, 0x0b, + 0xd8, 0xf4, 0x32, 0x02, 0xf4, 0x0e, 0xd2, 0xf1, + 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x01, 0xfa, 0xf9, 0x00, 0xbd, 0xa4, 0xf8, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 +}; + +static const uint8_t nvc0_ctxctl_code_09[] = +{ + 0xf1, 0x07, 0x00, 0x10, 0xf1, 0x03, 0x00, 0x00, + 0xfe, 0x04, 0x00, 0xbd, 0xa4, 0xf5, 0x21, 0x9e, + 0x32, 0xf8, 0x02, 0xf8, 0x00, 0xf9, 0x00, 0xf1, + 0x97, 0x2c, 0x03, 0xb0, 0xa6, 0x01, 0xf4, 0x0b, + 0x39, 0xf1, 0x97, 0xf8, 0x06, 0xb0, 0xa6, 0x02, + 0xf4, 0x0b, 0x2f, 0xb0, 0xa6, 0x09, 0xf4, 0x0b, + 0x08, 0xbd, 0x94, 0xf4, 0x0e, 0x24, 0xf1, 0x97, + 0xd8, 0x01, 0x98, 0x90, 0x00, 0xf1, 0xb7, 0x62, + 0x00, 0x92, 0x0a, 0x00, 0xf5, 0x21, 0x1e, 0x34, + 0xbc, 0x00, 0x90, 0xb6, 0xa4, 0x02, 0xbb, 0x90, + 0x00, 0xb6, 0x94, 0x03, 0xbc, 0xa9, 0x90, 0xfc, + 0x00, 0x97, 0x9a, 0x08, 0xb6, 0xa0, 0x01, 0xb6, + 0xa4, 0x08, 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x85, + 0xf0, 0xf3, 0x01, 0xf0, 0x97, 0x20, 0xfa, 0xf9, + 0x00, 0xf1, 0x97, 0x70, 0x02, 0x92, 0xaf, 0x00, + 0x80, 0x9a, 0x00, 0xf4, 0x0e, 0x06, 0xb6, 0xf2, + 0x01, 0xb0, 0xf6, 0x00, 0xf4, 0x1b, 0xfa, 0xf1, + 0x97, 0x70, 0x02, 0x80, 0x9f, 0x00, 0xf1, 0xf7, + 0x00, 0x85, 0xf0, 0xf3, 0x01, 0xf1, 0x97, 0x20, + 0x0a, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf1, 0x97, + 0xfc, 0x47, 0xf0, 0x93, 0x02, 0xfa, 0x9a, 0x00, + 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x03, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, 0xf3, 0x02, + 0x92, 0xd0, 0x00, 0xf1, 0x97, 0x00, 0x02, 0xb4, + 0xd0, 0x02, 0xfa, 0xf9, 0x00, 0xf0, 0xf7, 0x01, + 0xb0, 0xd6, 0x02, 0xf5, 0x0b, 0x46, 0x00, 0xb8, + 0xdf, 0x06, 0xf4, 0x0b, 0x08, 0xbd, 0xf4, 0xf4, + 0x0e, 0x3a, 0xb0, 0xe6, 0x00, 0xf4, 0x1b, 0x0d, + 0xf0, 0xf7, 0x02, 0xf1, 0xf3, 0x00, 0x80, 0xf4, + 0x0e, 0x2a, 0xb0, 0xe6, 0x03, 0xf4, 0x1b, 0x0d, + 0xf0, 0xf7, 0x03, 0xf1, 0xf3, 0x00, 0x80, 0xf4, + 0x0e, 0x1a, 0xb0, 0xe6, 0x02, 0xf4, 0x1b, 0x0d, + 0xf0, 0xf7, 0x04, 0xf1, 0xf3, 0x00, 0x80, 0xf4, + 0x0e, 0x0a, 0xf0, 0xf7, 0x00, 0xf1, 0xf3, 0x00, + 0x80, 0xf1, 0x97, 0x00, 0x88, 0xf0, 0x93, 0x02, + 0xfa, 0x9f, 0x00, 0xfe, 0xa7, 0x00, 0xbd, 0x94, + 0xfe, 0x9b, 0x00, 0xf1, 0xf7, 0x00, 0x43, 0xfa, + 0xf9, 0x00, 0xb4, 0x90, 0x03, 0xb6, 0xc4, 0x10, + 0xb0, 0x96, 0x01, 0xf4, 0x1b, 0x0c, 0xff, 0x0c, + 0x95, 0xfa, 0xb9, 0x05, 0xf4, 0x0e, 0x09, 0xff, + 0x0c, 0x95, 0xfa, 0xb9, 0x06, 0xb4, 0x90, 0x04, + 0xb0, 0x96, 0x02, 0xf4, 0x1b, 0x05, 0xf8, 0x03, + 0xf1, 0xf7, 0x00, 0x88, 0xf0, 0xf3, 0x02, 0xbd, + 0x94, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x02, + 0xb7, 0xf2, 0x00, 0x75, 0xfa, 0xf9, 0x00, 0xfc, + 0x00, 0xf8, 0x00, 0xf4, 0x30, 0xf4, 0xf1, 0xf7, + 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x08, + 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x02, 0xb0, 0xa1, + 0x02, 0xb0, 0x91, 0x00, 0xb0, 0x91, 0x01, 0xbd, + 0xa4, 0xbd, 0xb4, 0xf0, 0xc7, 0x06, 0xf1, 0xd7, + 0x00, 0x05, 0xbd, 0xe4, 0xf5, 0x21, 0xb7, 0x00, + 0xf1, 0xf7, 0x00, 0x13, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x08, 0xfa, 0xf9, 0x00, 0xf4, 0x30, 0x0c, + 0xf8, 0x00, 0xf4, 0x30, 0xf4, 0xf1, 0xf7, 0x00, + 0x0b, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x02, 0xfa, + 0xf9, 0x00, 0xf1, 0xb7, 0x00, 0x01, 0xb0, 0x91, + 0x00, 0xb0, 0xa1, 0x02, 0xb0, 0x91, 0x01, 0xbd, + 0xa4, 0xf0, 0xc7, 0x06, 0xf1, 0xd7, 0x00, 0x03, + 0xbd, 0xe4, 0xf5, 0x21, 0xb7, 0x00, 0xf1, 0xf7, + 0x00, 0x13, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x02, + 0xfa, 0xf9, 0x00, 0xf4, 0x30, 0x0c, 0xf8, 0x00, + 0xf4, 0x30, 0xf4, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, + 0xf0, 0x97, 0x02, 0xb0, 0x91, 0x00, 0xf0, 0x97, + 0x01, 0xb0, 0xa1, 0x02, 0xb0, 0x91, 0x01, 0xbd, + 0xa4, 0xf1, 0xb7, 0x00, 0x01, 0xf0, 0xc7, 0x06, + 0xf1, 0xd7, 0x00, 0x03, 0xbd, 0xe4, 0xf5, 0x21, + 0xb7, 0x00, 0xf1, 0xf7, 0x00, 0x13, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf4, + 0x30, 0x0c, 0xf8, 0x00, 0xf4, 0x30, 0xf4, 0xf1, + 0xf7, 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x04, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x02, 0xb0, + 0x91, 0x00, 0xf0, 0x97, 0x01, 0xb0, 0xa1, 0x02, + 0xb0, 0x91, 0x01, 0xbd, 0xa4, 0xbd, 0xb4, 0xf0, + 0xc7, 0x06, 0xf1, 0xd7, 0x00, 0x05, 0xbd, 0xe4, + 0xf5, 0x21, 0xb7, 0x00, 0xf1, 0xf7, 0x00, 0x13, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x04, 0xfa, 0xf9, + 0x00, 0xf4, 0x30, 0x0c, 0xf8, 0x00, 0xf1, 0x97, + 0xac, 0x01, 0xf0, 0xf7, 0x01, 0x80, 0x9f, 0x00, + 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x01, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf1, 0xd7, + 0xfc, 0x4a, 0xf0, 0xd3, 0x02, 0xf0, 0xe7, 0x0c, + 0xf0, 0x97, 0x0d, 0xb0, 0xa6, 0x00, 0xf4, 0x0b, + 0x08, 0xfa, 0xde, 0x00, 0xf8, 0x00, 0xfa, 0xd9, + 0x00, 0xf8, 0x00, 0xf1, 0x97, 0xfc, 0x4f, 0xf0, + 0x93, 0x02, 0xfa, 0x9a, 0x00, 0xb0, 0xb6, 0x00, + 0xf4, 0x0b, 0x10, 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x0a, 0xf4, 0x0e, 0x0d, + 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x0b, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf1, + 0x97, 0x00, 0xcc, 0xf0, 0x93, 0x01, 0xfa, 0x9b, + 0x00, 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x00, 0xc0, + 0xe7, 0xaa, 0xe2, 0x02, 0xf0, 0xc4, 0x01, 0xb6, + 0xa4, 0x02, 0xfd, 0xc9, 0x05, 0xf1, 0x97, 0x00, + 0xca, 0xf0, 0x93, 0x01, 0xfd, 0xac, 0x05, 0xfa, + 0x9a, 0x00, 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0c, + 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, 0xf9, 0x00, + 0xf8, 0x00, 0xf0, 0x97, 0xff, 0xf1, 0x93, 0xff, + 0x3f, 0xf0, 0xf7, 0x00, 0xf1, 0xf3, 0x00, 0x80, + 0xff, 0xa9, 0x94, 0xf1, 0xe7, 0x00, 0x0c, 0xf0, + 0xe3, 0x01, 0xfd, 0x9f, 0x05, 0xb0, 0xa6, 0x00, + 0xf4, 0x0b, 0x06, 0xfa, 0xe9, 0x00, 0xf8, 0x00, + 0xf1, 0x97, 0xfc, 0x47, 0xf0, 0x93, 0x02, 0xfa, + 0x9a, 0x00, 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x04, 0xfa, 0xf9, 0x00, 0xf8, + 0x00, 0xf1, 0x97, 0x00, 0x1d, 0xf0, 0x93, 0x02, + 0xfa, 0x9b, 0x00, 0xf0, 0xa4, 0x0f, 0xb7, 0x90, + 0x00, 0x01, 0xfa, 0x9a, 0x00, 0xb7, 0x90, 0x00, + 0x0c, 0xfa, 0x9c, 0x00, 0xf8, 0x00, 0xf1, 0x97, + 0x00, 0x06, 0xf0, 0x93, 0x02, 0xfa, 0x9a, 0x00, + 0xf1, 0xf7, 0x00, 0x07, 0xf0, 0xf3, 0x03, 0xf0, + 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf1, + 0xe7, 0x00, 0x44, 0xf0, 0xe3, 0x02, 0xf1, 0xc7, + 0x00, 0x43, 0xf0, 0xc3, 0x02, 0xf1, 0xd7, 0x00, + 0x42, 0xf0, 0xd3, 0x02, 0xbd, 0x94, 0xff, 0xe9, + 0xff, 0xb0, 0xf6, 0x00, 0xf4, 0x1d, 0x16, 0x92, + 0xa9, 0x00, 0xfa, 0xda, 0x00, 0xfa, 0xca, 0x00, + 0xe3, 0xff, 0xe6, 0x02, 0xb6, 0x90, 0x01, 0xbc, + 0xf9, 0xa0, 0xb6, 0xd0, 0x04, 0xb6, 0xc0, 0x04, + 0xb6, 0xe0, 0x04, 0xf1, 0x97, 0x24, 0x44, 0xf0, + 0x93, 0x02, 0xb8, 0xe9, 0x06, 0xf4, 0x1b, 0xcf, + 0xf8, 0x00, 0xbd, 0x94, 0xff, 0xa9, 0xef, 0xf0, + 0x97, 0xff, 0xfa, 0xb9, 0x00, 0xbd, 0x94, 0xff, + 0xa9, 0xff, 0xb0, 0xf6, 0x00, 0xf5, 0x1b, 0x69, + 0x00, 0xf1, 0x97, 0x55, 0x55, 0xf1, 0x93, 0x55, + 0x55, 0xfa, 0xc9, 0x00, 0xbd, 0x94, 0xff, 0xa9, + 0x9f, 0xf1, 0xf7, 0x55, 0x55, 0xf1, 0xf3, 0x55, + 0x55, 0xb8, 0x9f, 0x06, 0xf5, 0x1b, 0x4a, 0x00, + 0xbd, 0x94, 0xfa, 0xb9, 0x00, 0xff, 0xa9, 0x9f, + 0xb8, 0x9f, 0x06, 0xf4, 0x1b, 0x3b, 0xf1, 0x97, + 0xaa, 0xaa, 0xf1, 0x93, 0xaa, 0xaa, 0xfa, 0xa9, + 0x00, 0xbd, 0x94, 0xff, 0xa9, 0x9f, 0xf1, 0xf7, + 0xaa, 0xaa, 0xf1, 0xf3, 0xaa, 0xaa, 0xb8, 0x9f, + 0x06, 0xf4, 0x1b, 0x1d, 0xf0, 0x97, 0xff, 0xfa, + 0xb9, 0x00, 0xbd, 0x94, 0xff, 0xa9, 0x9f, 0xb0, + 0x96, 0x00, 0xf4, 0x1b, 0x0c, 0xfa, 0xae, 0x00, + 0xf1, 0xa7, 0x00, 0x10, 0xf8, 0x00, 0xfa, 0xae, + 0x00, 0xf1, 0xa7, 0x00, 0x20, 0xf8, 0x00, 0xf1, + 0xf7, 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0xf1, 0x97, + 0x00, 0x40, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x00, + 0xf0, 0x93, 0x01, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, + 0xf0, 0x94, 0x04, 0xf4, 0x1b, 0xf2, 0xf1, 0xf7, + 0x00, 0x13, 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, + 0x40, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf1, 0xf7, + 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, + 0x80, 0xf0, 0x93, 0x00, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0xfc, 0x47, 0xf0, 0x93, 0x02, 0xfa, 0x9a, + 0x00, 0xf0, 0x97, 0x01, 0xb7, 0xf0, 0xfc, 0x3f, + 0xfa, 0xf9, 0x00, 0xf5, 0x21, 0x57, 0x04, 0xf1, + 0xf7, 0xfc, 0x46, 0xf0, 0xf3, 0x02, 0xbd, 0x94, + 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x05, 0xb7, 0xf0, + 0x00, 0x04, 0xfa, 0xf9, 0x00, 0xf5, 0x21, 0x57, + 0x04, 0xf1, 0xf7, 0x00, 0x13, 0xf0, 0xf3, 0x02, + 0xf1, 0x97, 0x00, 0x80, 0xf0, 0x93, 0x00, 0xfa, + 0xf9, 0x00, 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0b, + 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x20, 0xfa, + 0xf9, 0x00, 0xf1, 0x97, 0xfc, 0x47, 0xf0, 0x93, + 0x02, 0xfa, 0x9a, 0x00, 0xf0, 0x97, 0x01, 0xb7, + 0xf0, 0xfc, 0x3f, 0xfa, 0xf9, 0x00, 0xf5, 0x21, + 0x57, 0x04, 0xf1, 0xf7, 0xfc, 0x46, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0xff, 0xfa, 0xf9, 0x00, 0xf0, + 0x97, 0x02, 0xb7, 0xf0, 0x00, 0x04, 0xfa, 0xf9, + 0x00, 0xf1, 0x97, 0x00, 0x20, 0xb7, 0xf2, 0xfc, + 0x37, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xb0, 0xd6, + 0x00, 0xf0, 0xfc, 0x0b, 0xf0, 0xf6, 0x01, 0xf1, + 0x97, 0x00, 0xcc, 0xf0, 0x93, 0x01, 0xb6, 0xf0, + 0x02, 0xfa, 0x9b, 0x00, 0xf0, 0x97, 0x00, 0xf1, + 0x93, 0x00, 0x80, 0xf0, 0xf4, 0x03, 0xf0, 0xc4, + 0x01, 0xb6, 0xf4, 0x1d, 0xe7, 0xaa, 0xe2, 0x02, + 0xb6, 0xa4, 0x02, 0xfd, 0xca, 0x05, 0xfd, 0xc9, + 0x05, 0xf1, 0x97, 0x00, 0xca, 0xf0, 0x93, 0x01, + 0xfd, 0xfc, 0x05, 0xfa, 0x9f, 0x00, 0xf1, 0x97, + 0x00, 0xca, 0xf0, 0x93, 0x01, 0xbd, 0xf4, 0xff, + 0x9f, 0x9f, 0xf0, 0xf7, 0x00, 0xf1, 0xf3, 0x00, + 0x80, 0xfd, 0x9f, 0x04, 0xf4, 0x1b, 0xea, 0xb0, + 0xd6, 0x00, 0xf4, 0x0b, 0x14, 0xf0, 0x97, 0x00, + 0xf0, 0x93, 0x01, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, + 0xf0, 0x94, 0x80, 0xf4, 0x0b, 0xf2, 0xf8, 0x00, + 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x85, 0xf0, 0xf3, + 0x01, 0x92, 0xa0, 0x00, 0xf1, 0x97, 0x70, 0x02, + 0xfa, 0xf9, 0x00, 0xf1, 0xa7, 0x14, 0xa6, 0xf0, + 0xa3, 0x41, 0xf1, 0xb7, 0x20, 0x08, 0xbd, 0xc4, + 0xf0, 0xd7, 0x01, 0xf5, 0x21, 0x26, 0x05, 0xf1, + 0x97, 0x6c, 0x02, 0x92, 0x0f, 0x00, 0x80, 0x90, + 0x00, 0xf4, 0x0e, 0x06, 0xb6, 0xf2, 0x01, 0xb0, + 0xf6, 0x00, 0xf4, 0x1b, 0xfa, 0xf1, 0x97, 0x6c, + 0x02, 0x80, 0x9f, 0x00, 0xf1, 0xf7, 0x00, 0x85, + 0xf0, 0xf3, 0x01, 0xf1, 0x97, 0x70, 0x07, 0xfa, + 0xf9, 0x00, 0xf1, 0xa7, 0x14, 0xa6, 0xf0, 0xa3, + 0x41, 0xf1, 0xb7, 0x20, 0x0a, 0xbd, 0xc4, 0xf0, + 0xd7, 0x01, 0xf5, 0x21, 0x26, 0x05, 0xfc, 0x00, + 0xf8, 0x00, 0xf0, 0xa7, 0x08, 0xf5, 0x21, 0x98, + 0x05, 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x02, 0xf1, + 0x97, 0x00, 0x01, 0xfa, 0xf9, 0x00, 0xf8, 0x00, + 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x00, 0x80, 0xe7, + 0xaa, 0xe2, 0x02, 0xf0, 0xb4, 0x01, 0xb6, 0xa4, + 0x02, 0xfd, 0xb9, 0x05, 0xf1, 0x97, 0x00, 0xca, + 0xf0, 0x93, 0x01, 0xfd, 0xab, 0x05, 0xfa, 0x9a, + 0x00, 0xf1, 0x97, 0x00, 0xca, 0xf0, 0x93, 0x01, + 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf0, 0xf7, 0x00, + 0xf1, 0xf3, 0x00, 0x80, 0xfd, 0x9f, 0x04, 0xf4, + 0x1b, 0xea, 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x01, + 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf0, 0x94, 0x40, + 0xf4, 0x0b, 0xf2, 0xf1, 0xa7, 0x00, 0xcb, 0xf0, + 0xa3, 0x01, 0xff, 0xaf, 0xaf, 0xf8, 0x00, 0xf1, + 0xa7, 0x70, 0x41, 0xf0, 0xa3, 0x40, 0xbd, 0xb4, + 0xf5, 0x21, 0x18, 0x06, 0xf0, 0xa4, 0x10, 0xf4, + 0x1b, 0xf0, 0xf8, 0x00, 0xc4, 0xa9, 0x03, 0xf9, + 0x00, 0xbd, 0xc4, 0x92, 0xb0, 0x00, 0xf1, 0xa7, + 0x70, 0x41, 0xf0, 0xa3, 0x40, 0xf0, 0xd7, 0x01, + 0xc5, 0x9b, 0x10, 0xf5, 0x21, 0x26, 0x05, 0xb0, + 0x06, 0x01, 0xf4, 0x1b, 0x16, 0xf1, 0xa7, 0x70, + 0x41, 0xf0, 0xa3, 0x40, 0xbd, 0xb4, 0xf5, 0x21, + 0x18, 0x06, 0xf0, 0xa4, 0x10, 0xf4, 0x1b, 0xf0, + 0xfc, 0x00, 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0b, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x00, 0xf0, 0x93, + 0x04, 0xfa, 0xf9, 0x00, 0xbd, 0xa4, 0xf0, 0xb7, + 0x01, 0xf5, 0x21, 0x84, 0x06, 0xf1, 0xf7, 0x00, + 0x13, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x00, 0xf0, + 0x93, 0x04, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, + 0xf1, 0x97, 0x00, 0x80, 0xf0, 0x93, 0x00, 0xfa, + 0xf9, 0x00, 0xf5, 0x21, 0xbc, 0x06, 0xf1, 0xa7, + 0x14, 0x96, 0xf0, 0xa3, 0x40, 0xf1, 0xb7, 0x70, + 0x07, 0xbd, 0xc4, 0xf0, 0xd7, 0x01, 0xf1, 0x07, + 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, 0x14, 0xa6, + 0xf0, 0xa3, 0x41, 0xf1, 0xb7, 0x20, 0x0a, 0xbd, + 0xc4, 0xf0, 0xd7, 0x01, 0xf9, 0x05, 0xf1, 0xa7, + 0x10, 0x8a, 0xf0, 0xa3, 0x40, 0xf1, 0xb7, 0x40, + 0x04, 0xbd, 0xc4, 0xf0, 0xd7, 0x01, 0xf9, 0x05, + 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x01, 0xfa, 0xf9, 0x00, 0xb7, 0xf0, 0x00, 0x12, + 0xb7, 0x90, 0xff, 0x7f, 0xfa, 0xf9, 0x00, 0xfc, + 0x00, 0xf8, 0x00, 0x92, 0xab, 0x00, 0xf1, 0xf7, + 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x80, + 0x00, 0xfa, 0xf9, 0x00, 0xbd, 0xa4, 0xf5, 0x21, + 0x84, 0x06, 0xf1, 0xf7, 0x00, 0x13, 0xf0, 0xf3, + 0x02, 0xf1, 0x97, 0x80, 0x00, 0xfa, 0xf9, 0x00, + 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x02, 0xfa, + 0xf9, 0x00, 0xf0, 0xa7, 0x01, 0x92, 0xab, 0x00, + 0xf5, 0x21, 0x84, 0x06, 0xf1, 0xf7, 0x00, 0x13, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x00, 0xf0, 0x93, + 0x02, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0x92, 0xab, + 0x00, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, 0xf3, 0x02, + 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x01, 0xfa, 0xf9, + 0x00, 0xf0, 0xa7, 0x02, 0xf5, 0x21, 0x84, 0x06, + 0xf1, 0xf7, 0x00, 0x13, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x00, 0xf0, 0x93, 0x01, 0xfa, 0xf9, 0x00, + 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, 0xf3, + 0x02, 0xf1, 0x97, 0x40, 0x00, 0xfa, 0xf9, 0x00, + 0xf0, 0xa7, 0x03, 0xf0, 0xb7, 0x01, 0xf5, 0x21, + 0x84, 0x06, 0xf1, 0xf7, 0x00, 0x13, 0xf0, 0xf3, + 0x02, 0xf1, 0x97, 0x40, 0x00, 0xfa, 0xf9, 0x00, + 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, 0xf3, + 0x02, 0xf1, 0x97, 0x00, 0x04, 0xfa, 0xf9, 0x00, + 0xf1, 0xa7, 0x60, 0x41, 0xf0, 0xa3, 0x40, 0xf0, + 0xb7, 0x01, 0xbd, 0xc4, 0xbd, 0xd4, 0xf5, 0x21, + 0x26, 0x05, 0xf1, 0xa7, 0x60, 0x41, 0xf0, 0xa3, + 0x40, 0xbd, 0xb4, 0xf5, 0x21, 0x18, 0x06, 0xf0, + 0xa4, 0x10, 0xf4, 0x0b, 0xf0, 0xf1, 0xf7, 0x00, + 0x13, 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x04, + 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xe4, + 0xbf, 0xff, 0xf0, 0xf1, 0x97, 0x39, 0x90, 0xf0, + 0x93, 0x00, 0xb8, 0xf9, 0x06, 0xf4, 0x0b, 0x2a, + 0xb8, 0xf9, 0x06, 0xf4, 0x0c, 0x09, 0xb6, 0x92, + 0x0c, 0xf4, 0x0e, 0x13, 0xf1, 0x97, 0x97, 0x90, + 0xf0, 0x93, 0x00, 0xb8, 0xf9, 0x06, 0xf4, 0x0b, + 0x11, 0xb6, 0x90, 0x29, 0xb8, 0xf9, 0x06, 0xf4, + 0x0b, 0x08, 0xbd, 0xb4, 0xf4, 0x0e, 0x22, 0xe4, + 0xbe, 0xff, 0xff, 0x94, 0xa9, 0x02, 0xf0, 0xf7, + 0x00, 0xf1, 0xf3, 0x00, 0x40, 0xb7, 0x90, 0x00, + 0x34, 0xfd, 0xef, 0x05, 0xe7, 0x99, 0x62, 0x01, + 0xb6, 0x94, 0x10, 0xff, 0x9e, 0xb5, 0xf1, 0xa7, + 0x88, 0x44, 0xf0, 0xa3, 0x40, 0xbd, 0xc4, 0xbd, + 0xd4, 0xf5, 0x21, 0x26, 0x05, 0xf1, 0x07, 0x18, + 0x06, 0xf1, 0xa7, 0x88, 0x44, 0xf0, 0xa3, 0x40, + 0xbd, 0xb4, 0xf9, 0x05, 0xf0, 0x97, 0x00, 0xf1, + 0x93, 0x00, 0x40, 0xfd, 0xa9, 0x04, 0xf4, 0x1b, + 0xe7, 0xf1, 0xa7, 0x8c, 0x44, 0xf0, 0xa3, 0x40, + 0xbd, 0xb4, 0xf9, 0x05, 0xfc, 0x00, 0xf8, 0x00, + 0xf9, 0x00, 0xf1, 0x07, 0x3d, 0x08, 0xf9, 0x10, + 0xf9, 0x20, 0x92, 0xb2, 0x00, 0xf9, 0x30, 0x92, + 0xa3, 0x00, 0xf0, 0xa7, 0x01, 0xf9, 0x05, 0x92, + 0x2b, 0x00, 0x92, 0xa1, 0x00, 0xf0, 0xa7, 0x02, + 0xf9, 0x05, 0xbd, 0xb4, 0x92, 0xa0, 0x00, 0x92, + 0x3a, 0x00, 0xf5, 0x21, 0x18, 0x06, 0xfd, 0x10, + 0x04, 0xbd, 0xc4, 0xb9, 0x00, 0x00, 0xbd, 0xd4, + 0xff, 0xa0, 0xb4, 0x92, 0x3a, 0x00, 0xff, 0x1b, + 0xb5, 0xf5, 0x21, 0x26, 0x05, 0xfc, 0x30, 0xfc, + 0x20, 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, 0xf9, + 0x00, 0x92, 0xa0, 0x00, 0xf0, 0xa7, 0x01, 0xf5, + 0x21, 0x3d, 0x08, 0xbd, 0xc4, 0x92, 0xab, 0x00, + 0xbd, 0xd4, 0x92, 0x0a, 0x00, 0xf5, 0x21, 0x26, + 0x05, 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf9, + 0x10, 0xe4, 0xcf, 0xff, 0xf0, 0xf1, 0x97, 0x39, + 0x90, 0xf0, 0x93, 0x00, 0xb8, 0xf9, 0x06, 0xf4, + 0x0b, 0x2a, 0xb8, 0xf9, 0x06, 0xf4, 0x0c, 0x09, + 0xb6, 0x92, 0x0c, 0xf4, 0x0e, 0x13, 0xf1, 0x97, + 0x97, 0x90, 0xf0, 0x93, 0x00, 0xb8, 0xf9, 0x06, + 0xf4, 0x0b, 0x11, 0xb6, 0x90, 0x29, 0xb8, 0xf9, + 0x06, 0xf4, 0x0b, 0x08, 0xbd, 0x14, 0xf4, 0x0e, + 0x22, 0x94, 0xa9, 0x02, 0xe4, 0xce, 0xff, 0xff, + 0xb7, 0x90, 0x00, 0x34, 0xf0, 0xf7, 0x00, 0xf1, + 0xf3, 0x00, 0x80, 0xe7, 0x99, 0x62, 0x01, 0xfd, + 0xef, 0x05, 0xb6, 0x94, 0x10, 0xff, 0x9e, 0x15, + 0xf1, 0xa7, 0x8c, 0x44, 0xf0, 0xa3, 0x40, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf1, 0x07, 0x26, 0x05, 0xf9, + 0x05, 0x92, 0x1b, 0x00, 0xf1, 0xa7, 0x88, 0x44, + 0xf0, 0xa3, 0x40, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, + 0x05, 0xf1, 0xa7, 0x88, 0x44, 0xf0, 0xa3, 0x40, + 0xbd, 0xb4, 0xf5, 0x21, 0x18, 0x06, 0xf0, 0x97, + 0x00, 0xf1, 0x93, 0x00, 0x80, 0xfd, 0xa9, 0x04, + 0xf4, 0x1b, 0xe9, 0xfc, 0x10, 0xfc, 0x00, 0xf8, + 0x00, 0xf9, 0x00, 0x92, 0xb0, 0x00, 0xbd, 0xb4, + 0xf5, 0x21, 0x18, 0x06, 0x92, 0x0c, 0x00, 0x92, + 0xab, 0x00, 0xf0, 0xa7, 0x01, 0xf5, 0x21, 0x3d, + 0x09, 0xfc, 0x00, 0xf8, 0x00, 0xf4, 0x30, 0xe0, + 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0xf9, + 0x00, 0xf1, 0x97, 0x00, 0x04, 0xf9, 0x10, 0xf9, + 0x20, 0xf9, 0x30, 0xf9, 0x40, 0xf9, 0x50, 0x92, + 0xb5, 0x00, 0xfa, 0xf9, 0x00, 0xf1, 0xa7, 0x00, + 0xa8, 0xf0, 0xa3, 0x41, 0xbd, 0xb4, 0xbd, 0xc4, + 0xbd, 0xd4, 0xf5, 0x21, 0x26, 0x05, 0xf1, 0xf7, + 0x00, 0x05, 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, 0xa3, + 0x41, 0xbd, 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, + 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, 0x04, + 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, 0x16, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xf0, 0x97, 0x00, + 0xf0, 0x93, 0x01, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, + 0xf1, 0x94, 0x00, 0x01, 0xf4, 0x0b, 0xf1, 0xfe, + 0x40, 0x01, 0xbd, 0x24, 0xf1, 0x17, 0x00, 0x28, + 0xf0, 0x13, 0x50, 0xb6, 0x00, 0x18, 0xf4, 0x0e, + 0x1d, 0xf5, 0x21, 0x18, 0x06, 0xf1, 0xf7, 0x9c, + 0x01, 0x98, 0xf9, 0x00, 0x80, 0x0a, 0x00, 0xb6, + 0x20, 0x01, 0xb6, 0x00, 0x04, 0xbb, 0x9a, 0x00, + 0x80, 0xf9, 0x00, 0xf1, 0x97, 0xd4, 0x01, 0x98, + 0x99, 0x00, 0x92, 0x1a, 0x00, 0xbd, 0xb4, 0xb7, + 0x10, 0x00, 0x80, 0xb8, 0x29, 0x06, 0xf4, 0x08, + 0xd3, 0xf1, 0xa7, 0x00, 0xa8, 0xf0, 0xa3, 0x41, + 0xbd, 0xc4, 0xbd, 0xd4, 0xf5, 0x21, 0x26, 0x05, + 0xf1, 0xf7, 0x00, 0x05, 0xf0, 0xf3, 0x01, 0xbd, + 0x94, 0xfa, 0xf9, 0x00, 0xbd, 0x44, 0xfe, 0x41, + 0x01, 0xbd, 0x34, 0xf1, 0x07, 0x00, 0x25, 0xf0, + 0x03, 0x50, 0xb6, 0x10, 0x18, 0xf4, 0x0e, 0x24, + 0xf9, 0x25, 0x90, 0x0a, 0x04, 0xf0, 0xb7, 0x18, + 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x25, 0x98, 0x19, + 0x00, 0xb6, 0x30, 0x01, 0xb7, 0x00, 0x00, 0x80, + 0xb6, 0x10, 0x04, 0xb6, 0x95, 0x08, 0xbb, 0x49, + 0x00, 0xf1, 0x97, 0xd4, 0x01, 0x98, 0x99, 0x00, + 0x92, 0x0a, 0x00, 0x92, 0x4b, 0x00, 0xbd, 0xc4, + 0xbd, 0xd4, 0xf1, 0x27, 0x26, 0x05, 0xb8, 0x39, + 0x06, 0xf4, 0x08, 0xc7, 0xf1, 0xf7, 0x9c, 0x01, + 0x98, 0xf9, 0x00, 0xb8, 0x59, 0x06, 0xf4, 0x0d, + 0x06, 0x80, 0xf5, 0x00, 0x98, 0xf9, 0x00, 0xf0, + 0xe7, 0x00, 0xf0, 0xe3, 0x02, 0xf1, 0xf7, 0x00, + 0x05, 0x80, 0xf9, 0x09, 0xfa, 0xe9, 0x00, 0xf1, + 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf1, 0x97, + 0x00, 0x04, 0xfa, 0xf9, 0x00, 0xfc, 0x50, 0xfc, + 0x40, 0xfc, 0x30, 0xfc, 0x20, 0xfc, 0x10, 0xfc, + 0x00, 0xf4, 0x30, 0x20, 0xf8, 0x00, 0xf4, 0x30, + 0xe0, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, + 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x08, 0xf9, 0x10, + 0xf9, 0x20, 0xf9, 0x30, 0xf9, 0x40, 0xfa, 0xf9, + 0x00, 0xf1, 0x07, 0x15, 0x00, 0xf0, 0xa7, 0x09, + 0xf9, 0x05, 0x92, 0xa3, 0x00, 0xf0, 0xa7, 0x02, + 0xf9, 0x05, 0xf1, 0xb7, 0x00, 0x03, 0xf1, 0x27, + 0xa8, 0x01, 0x98, 0xbc, 0x39, 0x98, 0x2d, 0x00, + 0xf1, 0x07, 0xa4, 0x01, 0x98, 0x01, 0x00, 0x97, + 0xae, 0x08, 0xc7, 0x39, 0xe8, 0xbb, 0xa3, 0x00, + 0xb6, 0x94, 0x10, 0xbc, 0xa1, 0x30, 0xbb, 0xda, + 0x00, 0xbb, 0xc3, 0x00, 0xe4, 0xef, 0xff, 0xff, + 0xf0, 0xe4, 0xff, 0xb6, 0xe4, 0x10, 0xfd, 0xf9, + 0x05, 0x80, 0x2d, 0x00, 0x80, 0xbf, 0x3b, 0x80, + 0xbc, 0x39, 0x80, 0xbe, 0x3a, 0x80, 0x03, 0x00, + 0xf1, 0xa7, 0x00, 0xa8, 0xf0, 0xa3, 0x41, 0xbd, + 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, 0xf5, 0x21, 0x26, + 0x05, 0xf1, 0xf7, 0x00, 0x05, 0xf0, 0xf3, 0x01, + 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xf1, 0xa7, 0x00, + 0xa5, 0xf0, 0xa3, 0x41, 0xbd, 0xb4, 0xbd, 0xc4, + 0xbd, 0xd4, 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, + 0xf1, 0xa7, 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, + 0xb7, 0x25, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, + 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x01, 0xbd, 0xf4, + 0xff, 0x9f, 0x9f, 0xf1, 0x94, 0x00, 0x01, 0xf4, + 0x0b, 0xf1, 0xfe, 0x40, 0x01, 0xbd, 0x24, 0xf1, + 0x17, 0x00, 0x28, 0xf0, 0x13, 0x50, 0xb6, 0x00, + 0x14, 0xf4, 0x0e, 0x1d, 0xf5, 0x21, 0x18, 0x06, + 0xf1, 0xf7, 0xa4, 0x01, 0x98, 0xf9, 0x00, 0x80, + 0x0a, 0x00, 0xb6, 0x20, 0x01, 0xb6, 0x00, 0x04, + 0xbb, 0x9a, 0x00, 0x80, 0xf9, 0x00, 0xf1, 0x97, + 0xd4, 0x01, 0x98, 0x99, 0x00, 0x92, 0x1a, 0x00, + 0xbd, 0xb4, 0xb7, 0x10, 0x00, 0x80, 0xb8, 0x29, + 0x06, 0xf4, 0x08, 0xd3, 0xf1, 0xa7, 0x00, 0xa8, + 0xf0, 0xa3, 0x41, 0xbd, 0xc4, 0xbd, 0xd4, 0xf5, + 0x21, 0x26, 0x05, 0x97, 0x30, 0x08, 0xf1, 0xf7, + 0x00, 0x05, 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xbd, 0x44, 0xfe, 0x42, 0x01, 0xf1, + 0x17, 0x00, 0x25, 0xf0, 0x13, 0x50, 0xb6, 0x20, + 0x14, 0xf4, 0x0e, 0x24, 0xf9, 0x35, 0x90, 0x1a, + 0x04, 0xf0, 0xb7, 0x27, 0xbd, 0xc4, 0xbd, 0xd4, + 0xf9, 0x35, 0x98, 0x29, 0x00, 0xb6, 0x40, 0x01, + 0xb7, 0x10, 0x00, 0x80, 0xb6, 0x20, 0x04, 0xb6, + 0x95, 0x08, 0xbb, 0x09, 0x00, 0xf1, 0x97, 0xd4, + 0x01, 0x98, 0x99, 0x00, 0x92, 0x1a, 0x00, 0x92, + 0x0b, 0x00, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, 0x37, + 0x26, 0x05, 0xb8, 0x49, 0x06, 0xf4, 0x08, 0xc7, + 0xf1, 0x97, 0xa4, 0x01, 0x98, 0x99, 0x00, 0xf1, + 0xf7, 0x00, 0x05, 0xf0, 0xe7, 0x00, 0xf0, 0xe3, + 0x02, 0x80, 0xf9, 0x0c, 0xfa, 0xe9, 0x00, 0xf1, + 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf1, 0x97, + 0x00, 0x08, 0xfa, 0xf9, 0x00, 0xfc, 0x40, 0xfc, + 0x30, 0xfc, 0x20, 0xfc, 0x10, 0xfc, 0x00, 0xf4, + 0x30, 0x20, 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0b, + 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x01, 0xfa, + 0xf9, 0x00, 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x01, + 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf1, 0x94, 0x00, + 0x10, 0xf4, 0x1b, 0xf1, 0xf1, 0xf7, 0x00, 0x13, + 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x01, 0xfa, + 0xf9, 0x00, 0xf8, 0x00, 0xf1, 0xf7, 0x00, 0x0b, + 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x08, 0xfa, + 0xf9, 0x00, 0xf5, 0x21, 0xfc, 0x0c, 0xf1, 0xa7, + 0x60, 0x41, 0xf0, 0xa3, 0x40, 0xbd, 0xb4, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf5, 0x21, 0x26, 0x05, 0xf1, + 0xf7, 0x00, 0x13, 0xf0, 0xf3, 0x02, 0xf1, 0x97, + 0x00, 0x08, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf9, + 0x00, 0x92, 0xa0, 0x00, 0xf5, 0x21, 0xfc, 0x0c, + 0xf1, 0x97, 0x00, 0x81, 0xf0, 0x93, 0x02, 0xfa, + 0x90, 0x00, 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x00, + 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0xf9, + 0x10, 0xf0, 0x97, 0x20, 0xf9, 0x20, 0x92, 0xb1, + 0x00, 0xf4, 0x30, 0xf4, 0x92, 0xc2, 0x00, 0xfa, + 0xf9, 0x00, 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x00, + 0x80, 0xff, 0xb9, 0x94, 0xf5, 0x0b, 0x09, 0x01, + 0xb0, 0xc6, 0x01, 0xf4, 0x1b, 0x07, 0xf5, 0x21, + 0xfa, 0x07, 0xf5, 0x21, 0xfc, 0x0c, 0xf1, 0xf7, + 0x00, 0x89, 0xf0, 0xf3, 0x02, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf1, 0x97, 0x00, 0xc1, 0xf0, 0x93, + 0x02, 0xfa, 0x91, 0x00, 0xb7, 0x92, 0x00, 0x3e, + 0xfa, 0x91, 0x00, 0xf0, 0x97, 0x07, 0xb7, 0xf2, + 0x00, 0x05, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x00, + 0x84, 0xf0, 0x93, 0x02, 0xbd, 0xf4, 0xff, 0x9f, + 0x9f, 0xf0, 0x94, 0x1f, 0xf4, 0x1b, 0xf1, 0xf1, + 0x97, 0x00, 0xc0, 0xf0, 0x93, 0x02, 0xfa, 0x91, + 0x00, 0xb0, 0x26, 0x01, 0xf5, 0x1b, 0xb1, 0x00, + 0xf1, 0x07, 0x5f, 0x0d, 0xbd, 0xa4, 0xf9, 0x05, + 0xf0, 0x97, 0x02, 0xc7, 0x1e, 0x3c, 0xf1, 0xb7, + 0x00, 0x02, 0xf0, 0xc7, 0x03, 0xf1, 0xd7, 0x00, + 0x04, 0xb0, 0x91, 0x02, 0x94, 0x1a, 0x04, 0xb0, + 0x21, 0x01, 0xb0, 0x21, 0x00, 0xf5, 0x21, 0xb7, + 0x00, 0xf1, 0x97, 0x00, 0x04, 0x98, 0x9f, 0x05, + 0x98, 0x99, 0x04, 0xb6, 0xf4, 0x18, 0xb6, 0x95, + 0x08, 0xfd, 0x9f, 0x05, 0xf1, 0xf7, 0xb0, 0x01, + 0x92, 0x9a, 0x00, 0x80, 0xf9, 0x00, 0xf9, 0x05, + 0xf1, 0x97, 0x00, 0x05, 0xf0, 0xa7, 0x02, 0xf1, + 0xf7, 0xde, 0xc0, 0xf1, 0xf3, 0x0d, 0x60, 0x80, + 0x9f, 0x3f, 0xf5, 0x21, 0x73, 0x01, 0xf5, 0x21, + 0xfc, 0x0c, 0xf1, 0xf7, 0x00, 0x84, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x05, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0xb0, 0x01, 0x98, 0x9b, 0x00, 0xf1, 0xa7, + 0x00, 0xa5, 0xf0, 0xa3, 0x41, 0xbd, 0xc4, 0xbd, + 0xd4, 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, + 0xa7, 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, + 0x13, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xf1, + 0x97, 0x00, 0x84, 0xf0, 0x93, 0x02, 0xbd, 0xf4, + 0xff, 0x9f, 0x9f, 0xb0, 0x96, 0x00, 0xf4, 0x1b, + 0xf1, 0xf5, 0x21, 0x2c, 0x0d, 0xf1, 0xf7, 0x00, + 0x12, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x20, 0xfa, + 0xf9, 0x00, 0xf4, 0x30, 0x0c, 0xfc, 0x20, 0xfc, + 0x10, 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf4, + 0x30, 0xf4, 0xf5, 0x21, 0xfa, 0x07, 0xbd, 0xd4, + 0xf1, 0xe7, 0x00, 0x04, 0xbd, 0xf4, 0xf0, 0x97, + 0x00, 0xf1, 0x93, 0x00, 0x80, 0xff, 0xf9, 0x95, + 0xb6, 0xf0, 0x04, 0x80, 0xe9, 0x00, 0xb6, 0xe0, + 0x04, 0xb6, 0xd0, 0x01, 0xb1, 0xd6, 0x40, 0x00, + 0xf4, 0x1b, 0xe6, 0xf1, 0x97, 0xb0, 0x01, 0x98, + 0x9a, 0x00, 0xf1, 0x07, 0xb7, 0x00, 0xf5, 0x21, + 0x5f, 0x0d, 0xf0, 0x97, 0x02, 0xb0, 0x91, 0x00, + 0xf0, 0x97, 0x01, 0xf0, 0xc7, 0x02, 0xb0, 0x91, + 0x02, 0xbd, 0xa4, 0xf1, 0xb7, 0x00, 0x01, 0xb0, + 0xc1, 0x01, 0xf1, 0xd7, 0x00, 0x04, 0xbd, 0xe4, + 0xf9, 0x05, 0xf0, 0x97, 0x02, 0xb0, 0x91, 0x00, + 0xf0, 0x97, 0x01, 0xf0, 0xc7, 0x02, 0xb0, 0x91, + 0x02, 0xbd, 0xa4, 0xf1, 0xb7, 0x10, 0x01, 0xb0, + 0xc1, 0x01, 0xf1, 0xd7, 0x10, 0x04, 0xbd, 0xe4, + 0xf9, 0x05, 0xf0, 0x97, 0x02, 0xb0, 0x91, 0x00, + 0xf0, 0x97, 0x01, 0xb0, 0x91, 0x02, 0xf0, 0x97, + 0x02, 0xbd, 0xa4, 0xf1, 0xb7, 0x20, 0x01, 0xb0, + 0x91, 0x01, 0xf0, 0xc7, 0x03, 0xf1, 0xd7, 0x20, + 0x04, 0xbd, 0xe4, 0xf9, 0x05, 0xf0, 0x97, 0x02, + 0xb0, 0x91, 0x00, 0xf0, 0x97, 0x01, 0xb0, 0x91, + 0x02, 0xf0, 0x97, 0x02, 0xbd, 0xa4, 0xf1, 0xb7, + 0x40, 0x01, 0xb0, 0x91, 0x01, 0xf0, 0xc7, 0x04, + 0xf1, 0xd7, 0x40, 0x04, 0xbd, 0xe4, 0xf9, 0x05, + 0xf0, 0x97, 0x02, 0xf0, 0xc7, 0x05, 0xf1, 0xd7, + 0x80, 0x04, 0xbd, 0xe4, 0xb0, 0x91, 0x00, 0xbd, + 0xa4, 0xf1, 0xb7, 0x80, 0x01, 0xb0, 0x91, 0x01, + 0xb0, 0x91, 0x02, 0xf9, 0x05, 0xbd, 0xc4, 0xf1, + 0xd7, 0x00, 0x04, 0xbd, 0xe4, 0x98, 0xdf, 0x00, + 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x00, 0x80, 0xb6, + 0xd0, 0x04, 0xff, 0xe9, 0x95, 0xb8, 0xf9, 0x06, + 0xf5, 0x1b, 0x0a, 0x01, 0xb6, 0xe0, 0x04, 0xb6, + 0xc0, 0x01, 0xb1, 0xc6, 0x40, 0x00, 0xf4, 0x1b, + 0xdf, 0xf1, 0xf7, 0x00, 0x04, 0xbd, 0x94, 0x80, + 0xf9, 0x00, 0xb6, 0xf0, 0x04, 0xf1, 0x97, 0x00, + 0x05, 0xb8, 0xf9, 0x06, 0xf4, 0x1b, 0xf1, 0xf0, + 0x97, 0x02, 0xb0, 0x91, 0x00, 0xf0, 0x97, 0x01, + 0xf1, 0x07, 0xb7, 0x00, 0xb0, 0x91, 0x01, 0xbd, + 0xa4, 0xf0, 0xc7, 0x02, 0xb0, 0x91, 0x02, 0xf1, + 0xb7, 0x00, 0x01, 0xf1, 0xd7, 0x00, 0x04, 0xbd, + 0xe4, 0xf9, 0x05, 0xf0, 0x97, 0x02, 0xb0, 0x91, + 0x00, 0xf0, 0x97, 0x01, 0xbd, 0xa4, 0xb0, 0x91, + 0x01, 0xf1, 0xb7, 0x10, 0x01, 0xf0, 0xc7, 0x02, + 0xb0, 0x91, 0x02, 0xf1, 0xd7, 0x10, 0x04, 0xbd, + 0xe4, 0xf9, 0x05, 0xf0, 0x97, 0x01, 0xb0, 0x91, + 0x01, 0xf0, 0x97, 0x02, 0xb0, 0x91, 0x00, 0xf0, + 0x97, 0x01, 0xbd, 0xa4, 0xf1, 0xb7, 0x20, 0x01, + 0xb0, 0x91, 0x02, 0xf0, 0xc7, 0x03, 0xf1, 0xd7, + 0x20, 0x04, 0xbd, 0xe4, 0xf9, 0x05, 0xf0, 0x97, + 0x01, 0xb0, 0x91, 0x01, 0xf0, 0x97, 0x02, 0xb0, + 0x91, 0x00, 0xf0, 0x97, 0x01, 0xbd, 0xa4, 0xf1, + 0xb7, 0x40, 0x01, 0xb0, 0x91, 0x02, 0xf0, 0xc7, + 0x04, 0xf1, 0xd7, 0x40, 0x04, 0xbd, 0xe4, 0xf9, + 0x05, 0xf0, 0x97, 0x02, 0xb0, 0x91, 0x00, 0xf0, + 0x97, 0x01, 0xf0, 0xc7, 0x05, 0xb0, 0x91, 0x01, + 0xf1, 0xd7, 0x80, 0x04, 0xf0, 0x97, 0x02, 0xbd, + 0xe4, 0xbd, 0xa4, 0xf1, 0xb7, 0x80, 0x01, 0xb0, + 0x91, 0x02, 0xf9, 0x05, 0xbd, 0xc4, 0xf1, 0xd7, + 0x00, 0x04, 0xbd, 0xe4, 0x98, 0xdf, 0x00, 0xf0, + 0x97, 0x00, 0xf1, 0x93, 0x00, 0x80, 0xb6, 0xd0, + 0x04, 0xff, 0xe9, 0x95, 0xb8, 0xf9, 0x06, 0xf4, + 0x1b, 0x1b, 0xb6, 0xe0, 0x04, 0xb6, 0xc0, 0x01, + 0xb1, 0xc6, 0x40, 0x00, 0xf4, 0x1b, 0xe0, 0xf5, + 0x21, 0x2c, 0x0d, 0xf1, 0xa7, 0x00, 0x10, 0xf4, + 0x0e, 0x0b, 0xf5, 0x21, 0x2c, 0x0d, 0xf1, 0xa7, + 0x00, 0x20, 0xf4, 0x30, 0x0c, 0xfc, 0x00, 0xf8, + 0x00, 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x05, 0xf0, + 0xf3, 0x01, 0xf9, 0x10, 0xbd, 0x94, 0xfa, 0xf9, + 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, 0xa3, 0x41, + 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, 0x07, 0x26, 0x05, + 0xf9, 0x05, 0xf1, 0xa7, 0x04, 0xa5, 0xf0, 0xa3, + 0x41, 0xf0, 0xb7, 0x29, 0xbd, 0xc4, 0xbd, 0xd4, + 0xf9, 0x05, 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x01, + 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf1, 0x94, 0x00, + 0x01, 0xf4, 0x0b, 0xf1, 0xbd, 0x14, 0xf1, 0x07, + 0x00, 0x28, 0xf0, 0x03, 0x50, 0xf4, 0x0e, 0x20, + 0xf5, 0x21, 0x18, 0x06, 0xb1, 0xa6, 0x00, 0x10, + 0xf4, 0x0b, 0x12, 0xf1, 0x97, 0x1c, 0x00, 0xf1, + 0xf7, 0x00, 0x20, 0x80, 0x9f, 0x00, 0xf5, 0x0e, + 0x5b, 0x00, 0xb6, 0x10, 0x01, 0xf1, 0x97, 0xd4, + 0x01, 0x98, 0x99, 0x00, 0x92, 0x0a, 0x00, 0xbd, + 0xb4, 0xb7, 0x00, 0x00, 0x80, 0xb8, 0x19, 0x06, + 0xf4, 0x08, 0xd0, 0xf0, 0x07, 0x00, 0xf0, 0x03, + 0x02, 0xa0, 0x0b, 0x00, 0x10, 0xa0, 0x0c, 0x00, + 0x08, 0x92, 0x0a, 0x00, 0xf1, 0x17, 0x1c, 0x00, + 0xf5, 0x21, 0xd2, 0x03, 0x80, 0x1a, 0x00, 0xb1, + 0xa6, 0x00, 0x20, 0xf4, 0x0b, 0x1e, 0xf1, 0x97, + 0x00, 0x07, 0xf0, 0x93, 0x02, 0xb8, 0x09, 0x06, + 0xf4, 0x0b, 0x0a, 0xb7, 0x00, 0x00, 0x01, 0xf4, + 0x0e, 0xd2, 0xf5, 0x21, 0xbd, 0x0e, 0x80, 0x1a, + 0x00, 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, 0xf9, + 0x00, 0xf1, 0x07, 0x3d, 0x08, 0xf9, 0x10, 0x92, + 0xb1, 0x00, 0xf9, 0x20, 0xf9, 0x30, 0x92, 0xa3, + 0x00, 0xf0, 0xa7, 0x01, 0xf9, 0x05, 0x92, 0x1b, + 0x00, 0x92, 0xa2, 0x00, 0xf0, 0xa7, 0x02, 0xf9, + 0x05, 0x92, 0xa0, 0x00, 0xf5, 0x21, 0xfa, 0x07, + 0xf5, 0x21, 0xfc, 0x0c, 0xf1, 0x97, 0x00, 0x89, + 0xf0, 0x93, 0x02, 0xfa, 0x92, 0x00, 0xb7, 0x92, + 0x00, 0x06, 0xfa, 0x90, 0x00, 0xb7, 0x90, 0x00, + 0x01, 0xfa, 0x93, 0x00, 0xf1, 0x97, 0x00, 0x84, + 0xf0, 0x93, 0x02, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, + 0xb0, 0x96, 0x00, 0xf4, 0x1b, 0xf1, 0xf5, 0x21, + 0x2c, 0x0d, 0xfc, 0x30, 0xfc, 0x20, 0xfc, 0x10, + 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, + 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0xf9, 0x10, 0xf1, + 0x97, 0x00, 0x40, 0x92, 0xb1, 0x00, 0xfa, 0xf9, + 0x00, 0xf0, 0xa7, 0x01, 0xf5, 0x21, 0xa6, 0x07, + 0xf1, 0xb7, 0x71, 0x07, 0xf1, 0xa7, 0x14, 0x96, + 0xf0, 0xa3, 0x40, 0xbd, 0xc4, 0xf0, 0xd7, 0x01, + 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, + 0x14, 0xa6, 0xf0, 0xa3, 0x41, 0xf1, 0xb7, 0x22, + 0x0a, 0xbd, 0xc4, 0xf0, 0xd7, 0x01, 0xf9, 0x05, + 0xf1, 0xa7, 0x10, 0x8a, 0xf0, 0xa3, 0x40, 0xf1, + 0xb7, 0x44, 0x04, 0xbd, 0xc4, 0xf0, 0xd7, 0x01, + 0xf9, 0x05, 0xf1, 0xf7, 0x00, 0x02, 0xf0, 0xf3, + 0x03, 0xf0, 0x97, 0x08, 0xfa, 0xf9, 0x00, 0xbd, + 0xe4, 0xf4, 0x0e, 0x06, 0xb6, 0xe0, 0x01, 0xf0, + 0x97, 0x00, 0xf0, 0x93, 0x03, 0xbd, 0xf4, 0xff, + 0x9f, 0x9f, 0xf1, 0x94, 0x00, 0x80, 0xf4, 0x1b, + 0x0c, 0xb8, 0xe1, 0x06, 0xf4, 0x1b, 0x18, 0xf4, + 0x0e, 0x09, 0xb8, 0xe1, 0x06, 0xf4, 0x1b, 0xdf, + 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x02, 0xf4, 0x0e, 0x0c, 0xf0, 0xf7, 0x00, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, + 0xf5, 0x21, 0x7a, 0x07, 0xf1, 0xf7, 0x00, 0x12, + 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x40, 0xfa, + 0xf9, 0x00, 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, + 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0xf1, + 0x97, 0x80, 0x00, 0xfa, 0xf9, 0x00, 0xf1, 0xf7, + 0x00, 0x02, 0xf0, 0xf3, 0x03, 0xf0, 0x97, 0x04, + 0xfa, 0xf9, 0x00, 0xbd, 0xe4, 0xf4, 0x0e, 0x06, + 0xb6, 0xe0, 0x01, 0xf0, 0x97, 0x00, 0xf0, 0x93, + 0x03, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf1, 0x94, + 0x00, 0x20, 0xf4, 0x1b, 0x0c, 0xb8, 0xeb, 0x06, + 0xf4, 0x1b, 0x18, 0xf4, 0x0e, 0x09, 0xb8, 0xeb, + 0x06, 0xf4, 0x1b, 0xdf, 0xf0, 0xf7, 0x00, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x0a, 0xf4, 0x0e, 0x0c, + 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x05, 0xfa, 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x12, + 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x80, 0x00, 0xfa, + 0xf9, 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, + 0x00, 0x0b, 0xf0, 0xf3, 0x02, 0xf9, 0x10, 0x92, + 0xe0, 0x00, 0xf0, 0x97, 0x10, 0xfa, 0xf9, 0x00, + 0xf1, 0x97, 0xd8, 0x01, 0x98, 0x9f, 0x00, 0xb0, + 0xa6, 0x02, 0xf0, 0x1c, 0x0b, 0xf0, 0x97, 0x01, + 0xbb, 0x9f, 0x04, 0x92, 0x9a, 0x01, 0xb0, 0xb6, + 0x09, 0xf4, 0x1b, 0x1e, 0xf1, 0xf7, 0x00, 0xc4, + 0xf0, 0xf3, 0x01, 0xf0, 0x97, 0x00, 0xf0, 0x93, + 0x1a, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x10, + 0xb7, 0xf0, 0x00, 0x02, 0xf4, 0x0e, 0x27, 0xb0, + 0xb6, 0x0a, 0xf4, 0x0b, 0x08, 0xbd, 0xe4, 0xf4, + 0x0e, 0x2c, 0xf1, 0xf7, 0x00, 0xc4, 0xf0, 0xf3, + 0x01, 0xf1, 0x97, 0x00, 0xc0, 0xf0, 0x93, 0x1b, + 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x02, 0xb7, + 0xf0, 0x00, 0x02, 0xfa, 0xf9, 0x00, 0xf1, 0x97, + 0x00, 0xc7, 0xf0, 0x93, 0x01, 0xfa, 0x9a, 0x00, + 0xf0, 0xe7, 0x03, 0x92, 0xc9, 0x01, 0xb0, 0x96, + 0x01, 0xf4, 0x0c, 0x17, 0x94, 0x19, 0x10, 0xf1, + 0xf7, 0x00, 0x10, 0xf0, 0xf3, 0x02, 0xfd, 0x9f, + 0x05, 0xb7, 0xf2, 0x00, 0x4b, 0xfa, 0xf9, 0x00, + 0xbd, 0xa4, 0xbd, 0xb4, 0xf4, 0x0e, 0x32, 0x98, + 0xdf, 0x00, 0xf4, 0x0e, 0x10, 0xf1, 0x97, 0x00, + 0xc5, 0xf0, 0x93, 0x01, 0xff, 0x9b, 0x9f, 0xc4, + 0x9b, 0x1f, 0xb0, 0xb6, 0x00, 0xf4, 0x0b, 0xf0, + 0xfd, 0xfe, 0x05, 0xf1, 0x97, 0x00, 0xc8, 0xf0, + 0x93, 0x01, 0xfa, 0x9f, 0x00, 0xb6, 0xb2, 0x01, + 0xb6, 0xa0, 0x01, 0xb6, 0xd0, 0x04, 0xb8, 0xa0, + 0x06, 0xf4, 0x1e, 0xce, 0xb0, 0xc6, 0x01, 0xf4, + 0x0b, 0x1b, 0xb0, 0xc6, 0x03, 0xf4, 0x1b, 0x2f, + 0xf4, 0x0e, 0x12, 0xf1, 0x97, 0x00, 0xc5, 0xf0, + 0x93, 0x01, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xc4, + 0x9b, 0x1f, 0xb0, 0xb6, 0x10, 0xf4, 0x1b, 0xee, + 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x01, 0xbd, 0xf4, + 0xff, 0x9f, 0x9f, 0xf0, 0x94, 0x20, 0xf4, 0x0b, + 0x35, 0xf4, 0x0e, 0xef, 0xf1, 0xf7, 0x00, 0x10, + 0xf0, 0xf3, 0x04, 0x94, 0x19, 0x10, 0xfd, 0x9f, + 0x05, 0xf1, 0xf7, 0x00, 0xc5, 0xf0, 0xf3, 0x01, + 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x00, 0xc5, 0xf0, + 0x93, 0x01, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf0, + 0xf7, 0x00, 0xf0, 0xf3, 0x04, 0xfd, 0x9f, 0x04, + 0xf4, 0x1b, 0xeb, 0xf1, 0xf7, 0x00, 0x13, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x10, 0xfa, 0xf9, 0x00, + 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, 0xf0, 0x97, + 0xff, 0xf1, 0x93, 0xff, 0x3f, 0xfd, 0xb9, 0x04, + 0xf1, 0x97, 0x00, 0x1d, 0xf0, 0x93, 0x02, 0xfa, + 0x9b, 0x00, 0xf1, 0xf7, 0x00, 0x1e, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x0c, 0xfa, 0xf9, 0x00, 0xf0, + 0x97, 0x00, 0xf1, 0x93, 0x04, 0x03, 0xb7, 0xf0, + 0x00, 0x0c, 0xfa, 0xf9, 0x00, 0xbd, 0x94, 0xb7, + 0xf2, 0x00, 0x0d, 0xfa, 0xf9, 0x00, 0xf0, 0x97, + 0x04, 0xb7, 0xf0, 0x00, 0x01, 0xfa, 0xf9, 0x00, + 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x00, 0x07, 0xb7, + 0xf0, 0x00, 0x0c, 0xfa, 0xf9, 0x00, 0xf0, 0x97, + 0x01, 0xb7, 0xf2, 0x00, 0x2a, 0xfa, 0xf9, 0x00, + 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x0a, + 0xf0, 0xf3, 0x02, 0xf9, 0x10, 0xf1, 0x97, 0x00, + 0x01, 0xfa, 0xf9, 0x00, 0xf1, 0xa7, 0x00, 0xa8, + 0xf0, 0xa3, 0x41, 0xbd, 0xb4, 0xbd, 0xc4, 0xbd, + 0xd4, 0xf5, 0x21, 0x26, 0x05, 0xf1, 0xf7, 0x00, + 0x05, 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, 0xf9, + 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, 0xa3, 0x41, + 0xbd, 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, 0x07, + 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, 0x04, 0xa5, + 0xf0, 0xa3, 0x41, 0xf0, 0xb7, 0x11, 0xbd, 0xc4, + 0xbd, 0xd4, 0xf9, 0x05, 0xf1, 0xa7, 0x14, 0x8a, + 0xf0, 0xa3, 0x40, 0xf0, 0xb7, 0x10, 0xbd, 0xc4, + 0xbd, 0xd4, 0xf9, 0x05, 0xf1, 0xf7, 0x00, 0x1b, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x10, 0xfa, 0xf9, + 0x00, 0xf0, 0x97, 0x0c, 0xb7, 0xf0, 0xfc, 0x2f, + 0xfa, 0xf9, 0x00, 0xf1, 0x07, 0x57, 0x04, 0xf9, + 0x05, 0xbd, 0xa4, 0xf5, 0x21, 0xdc, 0x04, 0xf9, + 0x05, 0xf0, 0xb7, 0x01, 0xf0, 0xa7, 0x0f, 0xf1, + 0x17, 0xab, 0x02, 0xf9, 0x15, 0xf9, 0x05, 0xbd, + 0xa4, 0xf5, 0x21, 0x86, 0x04, 0xf9, 0x05, 0xf0, + 0xa7, 0x0f, 0xbd, 0xb4, 0xf9, 0x15, 0xf9, 0x05, + 0xf0, 0xa7, 0x03, 0xf0, 0xb7, 0x01, 0xf9, 0x15, + 0xf9, 0x05, 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x0d, 0xfa, 0xf9, 0x00, 0xf0, + 0xa7, 0x08, 0xf5, 0x21, 0x98, 0x05, 0xf1, 0xf7, + 0x00, 0x1b, 0xf0, 0xf3, 0x02, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf1, 0xa7, 0x14, 0x8a, 0xf0, 0xa3, + 0x40, 0xbd, 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, 0xf5, + 0x21, 0x26, 0x05, 0xf0, 0x97, 0x00, 0xf0, 0x93, + 0x01, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf1, 0x94, + 0x00, 0x01, 0xf4, 0x0b, 0xf1, 0xf0, 0xf7, 0x00, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x01, 0xfa, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x09, 0xf0, 0xf3, 0x01, + 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xf1, 0xf7, 0x00, + 0x12, 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x01, + 0xfa, 0xf9, 0x00, 0xfc, 0x10, 0xfc, 0x00, 0xf8, + 0x00, 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, + 0xf3, 0x02, 0xf9, 0x10, 0xf1, 0x97, 0x00, 0x10, + 0xf9, 0x20, 0x92, 0xa2, 0x00, 0xf9, 0x30, 0x92, + 0xb3, 0x00, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x0c, + 0xb7, 0xf0, 0xfc, 0x3f, 0xfa, 0xf9, 0x00, 0xf1, + 0x07, 0x57, 0x04, 0xf9, 0x05, 0xbd, 0xb4, 0xf0, + 0xa7, 0x0f, 0xf1, 0x17, 0xab, 0x02, 0xf9, 0x15, + 0xf9, 0x05, 0xf0, 0xb7, 0x01, 0x92, 0x3a, 0x00, + 0xf9, 0x15, 0xf9, 0x05, 0xbd, 0xa4, 0xf5, 0x21, + 0xdc, 0x04, 0xf9, 0x05, 0xf0, 0xa7, 0x0f, 0xbd, + 0xb4, 0xf9, 0x15, 0xf9, 0x05, 0xf0, 0xa7, 0x03, + 0xf0, 0xb7, 0x01, 0xf9, 0x15, 0xf9, 0x05, 0xf1, + 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x0d, 0xfa, 0xf9, 0x00, 0xf5, 0x21, 0x57, 0x04, + 0xbd, 0xa4, 0xf1, 0xc7, 0x00, 0x44, 0xf0, 0xc3, + 0x02, 0xf1, 0xb7, 0xa4, 0x00, 0xf0, 0x17, 0x18, + 0xf0, 0x07, 0x14, 0xbd, 0x94, 0xff, 0xc9, 0xdf, + 0xb0, 0xd6, 0x00, 0xf5, 0x1d, 0x5b, 0x00, 0x97, + 0xb9, 0x02, 0x94, 0x9e, 0x02, 0xf1, 0x97, 0x00, + 0x03, 0xf1, 0xf7, 0x00, 0x03, 0xbb, 0xe9, 0x00, + 0xb6, 0xd4, 0x02, 0x97, 0x09, 0x02, 0xb6, 0x94, + 0x02, 0xbb, 0x9f, 0x00, 0xb0, 0x36, 0x08, 0xf4, + 0x1b, 0x12, 0x90, 0xb9, 0x04, 0x80, 0xe2, 0x00, + 0xb6, 0x97, 0x02, 0xb6, 0x94, 0x02, 0xf4, 0x0e, + 0x10, 0x80, 0x92, 0x00, 0xf1, 0xf7, 0x00, 0x03, + 0x97, 0x19, 0x02, 0xb6, 0x94, 0x02, 0xbb, 0x9f, + 0x00, 0x90, 0x2f, 0x01, 0x80, 0x9d, 0x00, 0x97, + 0xd9, 0x08, 0xbc, 0x9f, 0x20, 0xb6, 0x90, 0x01, + 0xb6, 0x94, 0x08, 0xbb, 0xa9, 0x00, 0xb6, 0xb0, + 0x08, 0xb6, 0x00, 0x08, 0xb6, 0x10, 0x08, 0xb6, + 0xc0, 0x04, 0xf1, 0x97, 0x24, 0x44, 0xf0, 0x93, + 0x02, 0xb8, 0xc9, 0x06, 0xf5, 0x1b, 0x87, 0xff, + 0xf1, 0xf7, 0x00, 0x13, 0xf0, 0xf3, 0x02, 0xf1, + 0x97, 0x00, 0x10, 0xfa, 0xf9, 0x00, 0xfc, 0x30, + 0xfc, 0x20, 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, + 0xf4, 0x30, 0xe0, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, + 0xf3, 0x02, 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x02, + 0xf9, 0x10, 0xf9, 0x20, 0xf9, 0x30, 0xf9, 0x40, + 0xf9, 0x50, 0x92, 0xb5, 0x00, 0xfa, 0xf9, 0x00, + 0xf0, 0xa7, 0x01, 0xf5, 0x21, 0x15, 0x00, 0xf1, + 0x17, 0x94, 0x01, 0xf1, 0xc7, 0x98, 0x01, 0x98, + 0x19, 0x00, 0x98, 0xcf, 0x00, 0xf1, 0xe7, 0x00, + 0x20, 0xf0, 0xe3, 0x02, 0xbd, 0xd4, 0xbb, 0x9a, + 0x00, 0xbb, 0xfa, 0x00, 0x80, 0x19, 0x00, 0x80, + 0xcf, 0x00, 0xff, 0xed, 0xef, 0xf1, 0x07, 0x00, + 0x03, 0xbd, 0xa4, 0x80, 0x0e, 0x01, 0xf0, 0xb7, + 0x03, 0xf5, 0x21, 0xf1, 0x15, 0x98, 0x09, 0x00, + 0x98, 0x1f, 0x00, 0xf1, 0xe7, 0x00, 0x80, 0xf0, + 0xe3, 0x02, 0xf1, 0xc7, 0x20, 0x00, 0xbb, 0xaf, + 0x00, 0xbb, 0x9a, 0x00, 0x80, 0x09, 0x00, 0x98, + 0xc9, 0x00, 0xb6, 0xc0, 0x04, 0xf0, 0x94, 0x07, + 0xb6, 0x94, 0x04, 0xf0, 0x95, 0x08, 0xfa, 0xe9, + 0x00, 0xf1, 0x97, 0x2c, 0x80, 0xf0, 0x93, 0x02, + 0xb6, 0xe0, 0x04, 0xb8, 0xe9, 0x06, 0xf4, 0x1b, + 0xe1, 0xf1, 0x97, 0xd4, 0x01, 0x98, 0x9e, 0x00, + 0xf1, 0x97, 0x98, 0x01, 0x98, 0x99, 0x00, 0xa0, + 0xad, 0x00, 0x02, 0x90, 0xef, 0x02, 0xf1, 0xf4, + 0xff, 0xff, 0xc7, 0x99, 0xe8, 0xb6, 0x94, 0x10, + 0xfd, 0xf9, 0x05, 0xf1, 0x97, 0x94, 0x01, 0xb6, + 0xe4, 0x08, 0xbc, 0xde, 0x30, 0x80, 0x93, 0x00, + 0xf1, 0x97, 0x00, 0x03, 0xf1, 0xa7, 0x00, 0xa8, + 0xf0, 0xa3, 0x41, 0x80, 0x9f, 0x03, 0xbd, 0xb4, + 0xbd, 0xc4, 0xbd, 0xd4, 0xf5, 0x21, 0x26, 0x05, + 0xf1, 0xf7, 0x00, 0x05, 0xf0, 0xf3, 0x01, 0xbd, + 0x94, 0xfa, 0xf9, 0x00, 0xf1, 0xa7, 0x00, 0xa5, + 0xf0, 0xa3, 0x41, 0xbd, 0xb4, 0xbd, 0xc4, 0xbd, + 0xd4, 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, + 0xa7, 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, + 0x10, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xf0, + 0x97, 0x00, 0xf0, 0x93, 0x01, 0xbd, 0xf4, 0xff, + 0x9f, 0x9f, 0xf1, 0x94, 0x00, 0x01, 0xf4, 0x0b, + 0xf1, 0xfe, 0x40, 0x01, 0xbd, 0x24, 0xf1, 0x17, + 0x00, 0x28, 0xf0, 0x13, 0x50, 0xb6, 0x00, 0x18, + 0xf4, 0x0e, 0x1d, 0xf5, 0x21, 0x18, 0x06, 0xf1, + 0xf7, 0x94, 0x01, 0x98, 0xf9, 0x00, 0x80, 0x0a, + 0x00, 0xb6, 0x20, 0x01, 0xb6, 0x00, 0x04, 0xbb, + 0x9a, 0x00, 0x80, 0xf9, 0x00, 0xf1, 0x97, 0xd4, + 0x01, 0x98, 0x99, 0x00, 0x92, 0x1a, 0x00, 0xbd, + 0xb4, 0xb7, 0x10, 0x00, 0x80, 0xb8, 0x29, 0x06, + 0xf4, 0x08, 0xd3, 0xf1, 0xa7, 0x00, 0xa8, 0xf0, + 0xa3, 0x41, 0xbd, 0xc4, 0xbd, 0xd4, 0xf5, 0x21, + 0x26, 0x05, 0x97, 0x30, 0x08, 0xf1, 0xf7, 0x00, + 0x05, 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, 0xf9, + 0x00, 0xbd, 0x44, 0xfe, 0x42, 0x01, 0xf1, 0x17, + 0x00, 0x25, 0xf0, 0x13, 0x50, 0xb6, 0x20, 0x18, + 0xf4, 0x0e, 0x24, 0xf9, 0x35, 0x90, 0x1a, 0x04, + 0xf0, 0xb7, 0x14, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, + 0x35, 0x98, 0x29, 0x00, 0xb6, 0x40, 0x01, 0xb7, + 0x10, 0x00, 0x80, 0xb6, 0x20, 0x04, 0xb6, 0x95, + 0x08, 0xbb, 0x09, 0x00, 0xf1, 0x97, 0xd4, 0x01, + 0x98, 0x9e, 0x00, 0x92, 0x1a, 0x00, 0x92, 0x0b, + 0x00, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, 0x37, 0x26, + 0x05, 0xb8, 0x4e, 0x06, 0xf4, 0x08, 0xc7, 0xf1, + 0xf7, 0x94, 0x01, 0x98, 0xf9, 0x00, 0xb8, 0x59, + 0x06, 0xf4, 0x0d, 0x06, 0x80, 0xf5, 0x00, 0x98, + 0xfd, 0x00, 0xf1, 0x97, 0x00, 0x03, 0x98, 0x90, + 0x01, 0x98, 0x99, 0x03, 0xf1, 0xf7, 0x00, 0x05, + 0xbd, 0xb4, 0x80, 0xfe, 0x02, 0x80, 0xfd, 0x01, + 0xf0, 0xc7, 0x14, 0xc7, 0x9f, 0xf0, 0xf1, 0xe7, + 0x00, 0x42, 0xf0, 0xe3, 0x02, 0xf1, 0x94, 0xff, + 0xff, 0xbc, 0x9f, 0xa0, 0xf4, 0x0e, 0x1f, 0x98, + 0x99, 0x00, 0x92, 0xef, 0x00, 0xbc, 0xa9, 0x90, + 0xfa, 0xe9, 0x00, 0xb7, 0xf0, 0x00, 0x01, 0xfa, + 0xf9, 0x00, 0xb6, 0xb0, 0x01, 0xb6, 0xc0, 0x08, + 0xb6, 0xe0, 0x04, 0x97, 0xc9, 0x02, 0xf1, 0xf7, + 0x00, 0x03, 0xb6, 0x94, 0x02, 0xbb, 0x9f, 0x00, + 0xb8, 0xb0, 0x06, 0xf4, 0x1b, 0xd4, 0xf0, 0x97, + 0x00, 0xf0, 0x93, 0x02, 0xfa, 0x9d, 0x00, 0xf1, + 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf1, 0x97, + 0x00, 0x02, 0xfa, 0xf9, 0x00, 0xfc, 0x50, 0xfc, + 0x40, 0xfc, 0x30, 0xfc, 0x20, 0xfc, 0x10, 0xfc, + 0x00, 0xf4, 0x30, 0x20, 0xf8, 0x00, 0xf1, 0x97, + 0x00, 0x06, 0xf0, 0x93, 0x02, 0xfa, 0x9a, 0x00, + 0xf1, 0xf7, 0x00, 0x07, 0xf0, 0xf3, 0x03, 0xf0, + 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, + 0x92, 0xa0, 0x00, 0xf9, 0x10, 0x92, 0xba, 0x00, + 0xf0, 0x97, 0x02, 0xfa, 0xf9, 0x00, 0xf1, 0x97, + 0x20, 0x02, 0x98, 0x9d, 0x00, 0xf1, 0x97, 0x1c, + 0x02, 0x98, 0x99, 0x00, 0xf1, 0xc7, 0xdc, 0x01, + 0xc4, 0xdf, 0x07, 0xf1, 0x17, 0x20, 0x02, 0x94, + 0xfe, 0x03, 0x90, 0xdb, 0x01, 0xbb, 0xec, 0x00, + 0xc7, 0x9c, 0x03, 0xf0, 0x94, 0x07, 0xb8, 0xf9, + 0x06, 0xf4, 0x1b, 0x29, 0xc7, 0xd9, 0x03, 0xb8, + 0x9c, 0x06, 0xf4, 0x0b, 0x20, 0xf1, 0xf7, 0x00, + 0x06, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x12, 0xfa, + 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x07, 0xf0, 0xf3, + 0x03, 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf4, + 0x0e, 0x17, 0x80, 0xea, 0x01, 0x80, 0xe0, 0x00, + 0x80, 0x1b, 0x00, 0xb0, 0xb6, 0x10, 0xf4, 0x1b, + 0x08, 0xbd, 0x94, 0x80, 0x19, 0x00, 0xf1, 0xf7, + 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x02, + 0xfa, 0xf9, 0x00, 0xfc, 0x10, 0xfc, 0x00, 0xf8, + 0x00, 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x02, 0xf9, + 0x10, 0xbd, 0xf4, 0xf9, 0x20, 0xff, 0x9f, 0x1f, + 0xc4, 0x19, 0x04, 0xf4, 0x0b, 0x1f, 0xf1, 0xa7, + 0x00, 0x1a, 0xff, 0xaf, 0xaf, 0xf1, 0xb7, 0x00, + 0x19, 0xff, 0xbf, 0xbf, 0xf5, 0x21, 0x87, 0x19, + 0xf1, 0xf7, 0x00, 0x1d, 0xf0, 0x97, 0x01, 0xfa, + 0xf9, 0x00, 0x95, 0x10, 0x08, 0xc4, 0x02, 0xff, + 0xf5, 0x0b, 0x49, 0x00, 0xc4, 0x09, 0x01, 0xf4, + 0x0b, 0x0f, 0xf0, 0xa7, 0x00, 0xf0, 0xa3, 0x01, + 0xbd, 0xb4, 0xf5, 0x21, 0x87, 0x19, 0xc4, 0x09, + 0x02, 0xf4, 0x0b, 0x0c, 0xf0, 0xa7, 0x04, 0xbd, + 0xb4, 0xf5, 0x21, 0x87, 0x19, 0xc4, 0x09, 0x04, + 0xf4, 0x0b, 0x0f, 0xf0, 0xa7, 0x02, 0xf0, 0xa3, + 0x01, 0xbd, 0xb4, 0xf5, 0x21, 0x87, 0x19, 0xc4, + 0x29, 0x80, 0xf4, 0x0b, 0x0f, 0xf0, 0xa7, 0x03, + 0xf0, 0xa3, 0x01, 0xbd, 0xb4, 0xf5, 0x21, 0x87, + 0x19, 0xf1, 0x97, 0x00, 0x01, 0xfa, 0x91, 0x00, + 0xfc, 0x20, 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, + 0xf9, 0x00, 0xf1, 0x07, 0x3d, 0x08, 0xf9, 0x10, + 0x92, 0xb1, 0x00, 0xf9, 0x20, 0x92, 0xa2, 0x00, + 0xf9, 0x30, 0xf0, 0xa7, 0x01, 0xf9, 0x40, 0xf9, + 0x50, 0xf4, 0x30, 0xf4, 0xf9, 0x05, 0x92, 0x1b, + 0x00, 0x92, 0xa5, 0x00, 0xf0, 0xa7, 0x02, 0xf9, + 0x05, 0xe7, 0x24, 0xa2, 0x01, 0x92, 0xa3, 0x00, + 0xc7, 0x29, 0x70, 0xf4, 0x0b, 0x0c, 0xb0, 0x96, + 0x01, 0xf4, 0x1b, 0x21, 0xf4, 0x0e, 0x11, 0xf1, + 0x97, 0xc0, 0x01, 0xbd, 0xf4, 0xbd, 0x14, 0x80, + 0x9f, 0x00, 0xf4, 0x0e, 0x2a, 0x95, 0x29, 0x14, + 0xb6, 0x94, 0x08, 0xa0, 0x91, 0x00, 0x01, 0xf4, + 0x0e, 0x1d, 0xf1, 0xf7, 0x00, 0x06, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x13, 0xfa, 0xf9, 0x00, 0xf1, + 0xf7, 0x00, 0x07, 0xf0, 0xf3, 0x03, 0xf0, 0x97, + 0x01, 0xfa, 0xf9, 0x00, 0xf5, 0x21, 0xfa, 0x07, + 0xf0, 0x97, 0x02, 0xf0, 0xf7, 0x01, 0xf1, 0x07, + 0xb7, 0x00, 0xb0, 0x91, 0x00, 0xb0, 0xf1, 0x01, + 0x92, 0x1b, 0x00, 0xb0, 0x91, 0x02, 0xbd, 0xa4, + 0xf0, 0xc7, 0x06, 0xf1, 0xd7, 0x00, 0x04, 0xbd, + 0xe4, 0xf9, 0x05, 0xf1, 0xf7, 0x00, 0x04, 0x94, + 0x4e, 0x02, 0xbb, 0xef, 0x00, 0x98, 0xed, 0x00, + 0xb9, 0x39, 0x00, 0xff, 0x53, 0xf4, 0x92, 0x1b, + 0x00, 0xfd, 0x9d, 0x04, 0xbd, 0xa4, 0xfd, 0xf9, + 0x05, 0xf0, 0xc7, 0x06, 0x80, 0xef, 0x00, 0xf0, + 0x97, 0x02, 0xf1, 0xd7, 0x00, 0x04, 0xbd, 0xe4, + 0xb0, 0x91, 0x00, 0xb0, 0x91, 0x01, 0xb0, 0x91, + 0x02, 0xf9, 0x05, 0xf5, 0x21, 0x2c, 0x0d, 0xf4, + 0x30, 0x0c, 0xfc, 0x50, 0xfc, 0x40, 0xfc, 0x30, + 0xfc, 0x20, 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, + 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, + 0x02, 0xf9, 0x10, 0xf1, 0x97, 0x00, 0x20, 0xf9, + 0x20, 0xf9, 0x30, 0xfa, 0xf9, 0x00, 0xf1, 0x07, + 0x18, 0x06, 0xbd, 0xb4, 0xf1, 0xa7, 0x04, 0x07, + 0xf0, 0xa3, 0x40, 0xf9, 0x05, 0xf1, 0xf7, 0x00, + 0x42, 0x92, 0xa9, 0x00, 0xf0, 0xf3, 0x40, 0xbd, + 0xb4, 0xe4, 0x91, 0xfc, 0x3f, 0xc7, 0xaa, 0x50, + 0xb6, 0xa4, 0x02, 0xbb, 0xaf, 0x00, 0xf9, 0x05, + 0xbd, 0xb4, 0xe4, 0xa2, 0xff, 0xff, 0xf1, 0xa7, + 0x08, 0x07, 0xf0, 0xa3, 0x40, 0xf9, 0x05, 0x92, + 0xa0, 0x00, 0xf1, 0xa7, 0x00, 0x07, 0xf0, 0xa3, + 0x40, 0xbd, 0xb4, 0xf5, 0x21, 0x18, 0x06, 0xf1, + 0x97, 0x7c, 0xfb, 0xf1, 0x93, 0x03, 0x03, 0xfd, + 0xa9, 0x04, 0xf4, 0x1b, 0xe8, 0xf1, 0x37, 0x26, + 0x05, 0xe4, 0x2f, 0xff, 0xf0, 0xf1, 0x97, 0x39, + 0x90, 0xf0, 0x93, 0x00, 0xb8, 0xf9, 0x06, 0xf5, + 0x0b, 0xb1, 0x00, 0xb8, 0xf9, 0x06, 0xf4, 0x0c, + 0x11, 0xb6, 0x92, 0x0c, 0xb8, 0xf9, 0x06, 0xf5, + 0x1b, 0x81, 0x01, 0xf5, 0x0e, 0xdc, 0x00, 0xf1, + 0x97, 0x97, 0x90, 0xf0, 0x93, 0x00, 0xb8, 0xf9, + 0x06, 0xf4, 0x0b, 0x11, 0xb6, 0x90, 0x29, 0xb8, + 0xf9, 0x06, 0xf5, 0x1b, 0x66, 0x01, 0xf5, 0x0e, + 0x43, 0x00, 0xb1, 0x16, 0x08, 0x23, 0xf5, 0x0b, + 0x11, 0x01, 0xb1, 0x16, 0x08, 0x23, 0xf4, 0x0c, + 0x17, 0xb1, 0x16, 0x00, 0x23, 0xf5, 0x0b, 0xe6, + 0x00, 0xb1, 0x16, 0x04, 0x23, 0xf5, 0x1b, 0x43, + 0x01, 0xf5, 0x0e, 0xe8, 0x00, 0xb1, 0x16, 0x10, + 0x23, 0xf5, 0x0b, 0x1b, 0x01, 0xb1, 0x16, 0x14, + 0x23, 0xf5, 0x0b, 0x21, 0x01, 0xb1, 0x16, 0x0c, + 0x23, 0xf5, 0x1b, 0x27, 0x01, 0xf5, 0x0e, 0xe8, + 0x00, 0xb1, 0x16, 0x08, 0x05, 0xf5, 0x0b, 0xd2, + 0x00, 0xb1, 0x16, 0x08, 0x05, 0xf4, 0x0c, 0x17, + 0xb1, 0x16, 0x00, 0x05, 0xf5, 0x0b, 0xa7, 0x00, + 0xb1, 0x16, 0x04, 0x05, 0xf5, 0x1b, 0x04, 0x01, + 0xf5, 0x0e, 0xa9, 0x00, 0xb1, 0x16, 0x10, 0x05, + 0xf5, 0x0b, 0xdc, 0x00, 0xb1, 0x16, 0x14, 0x05, + 0xf5, 0x0b, 0xe2, 0x00, 0xb1, 0x16, 0x0c, 0x05, + 0xf5, 0x1b, 0xe8, 0x00, 0xf5, 0x0e, 0xa9, 0x00, + 0xb1, 0x16, 0x84, 0x02, 0xf5, 0x0b, 0x93, 0x00, + 0xb1, 0x16, 0x84, 0x02, 0xf4, 0x0c, 0x17, 0xb1, + 0x16, 0x7c, 0x02, 0xf5, 0x0b, 0x68, 0x00, 0xb1, + 0x16, 0x80, 0x02, 0xf5, 0x1b, 0xc5, 0x00, 0xf5, + 0x0e, 0x6a, 0x00, 0xb1, 0x16, 0x8c, 0x02, 0xf5, + 0x0b, 0x9d, 0x00, 0xb1, 0x16, 0x90, 0x02, 0xf5, + 0x0b, 0xa3, 0x00, 0xb1, 0x16, 0x88, 0x02, 0xf5, + 0x1b, 0xa9, 0x00, 0xf5, 0x0e, 0x6a, 0x00, 0xb1, + 0x16, 0xe8, 0x08, 0xf5, 0x0b, 0x54, 0x00, 0xb1, + 0x16, 0xe8, 0x08, 0xf4, 0x0c, 0x15, 0xb1, 0x16, + 0xe0, 0x08, 0xf4, 0x0b, 0x29, 0xb1, 0x16, 0xe4, + 0x08, 0xf5, 0x1b, 0x87, 0x00, 0xf4, 0x0e, 0x2c, + 0xb1, 0x16, 0xf0, 0x08, 0xf5, 0x0b, 0x60, 0x00, + 0xb1, 0x16, 0xf4, 0x08, 0xf5, 0x0b, 0x66, 0x00, + 0xb1, 0x16, 0xec, 0x08, 0xf5, 0x1b, 0x6c, 0x00, + 0xf4, 0x0e, 0x2d, 0x92, 0x0a, 0x00, 0x92, 0x2b, + 0x00, 0xf5, 0x21, 0xd9, 0x09, 0xf5, 0x0e, 0xa0, + 0x00, 0x92, 0x0a, 0x00, 0x92, 0x2b, 0x00, 0xf5, + 0x21, 0x1f, 0x09, 0xf5, 0x0e, 0x92, 0x00, 0x92, + 0x0a, 0x00, 0x92, 0x2b, 0x00, 0xf5, 0x21, 0x97, + 0x11, 0xf5, 0x0e, 0x84, 0x00, 0x92, 0x0b, 0x00, + 0xf0, 0xa7, 0x29, 0xf5, 0x21, 0xd1, 0x10, 0xf1, + 0x97, 0x1c, 0x00, 0x98, 0x9b, 0x00, 0xf0, 0xa7, + 0x01, 0x92, 0x2c, 0x00, 0xf5, 0x21, 0x3d, 0x09, + 0xf5, 0x0e, 0x65, 0x00, 0x92, 0x0a, 0x00, 0x92, + 0x2b, 0x00, 0xf5, 0x21, 0xd0, 0x08, 0xf5, 0x0e, + 0x57, 0x00, 0x92, 0x0a, 0x00, 0x92, 0x2b, 0x00, + 0xf5, 0x21, 0xa8, 0x1a, 0xf5, 0x0e, 0x49, 0x00, + 0x92, 0x2c, 0x00, 0xbd, 0xa4, 0xf0, 0xb7, 0x01, + 0xf5, 0x21, 0x3d, 0x09, 0xbd, 0xd4, 0xf1, 0xa7, + 0x44, 0x01, 0xf0, 0xa3, 0x40, 0xf1, 0xb7, 0x00, + 0x01, 0xbd, 0xc4, 0xf9, 0x35, 0xf1, 0xf7, 0x00, + 0x07, 0xf0, 0xf3, 0x03, 0xf0, 0x97, 0x00, 0xf0, + 0x93, 0x02, 0xfa, 0xf9, 0x00, 0xf1, 0xf7, 0x00, + 0x12, 0xf0, 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x20, + 0xfa, 0xf9, 0x00, 0xfc, 0x30, 0xfc, 0x20, 0xfc, + 0x10, 0xfc, 0x00, 0xf8, 0x00, 0x92, 0x2c, 0x00, + 0xbd, 0xa4, 0xf0, 0xb7, 0x01, 0xf5, 0x21, 0x3d, + 0x09, 0xbd, 0xd4, 0xf1, 0xa7, 0x44, 0x01, 0xf0, + 0xa3, 0x40, 0xf1, 0xb7, 0x00, 0x01, 0xbd, 0xc4, + 0xf9, 0x35, 0xf4, 0x0e, 0xcb, 0xf9, 0x00, 0xf1, + 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0x92, 0xa0, + 0x00, 0xf9, 0x10, 0x92, 0xba, 0x00, 0xf0, 0x97, + 0x04, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x68, 0x02, + 0x98, 0x9d, 0x00, 0xf1, 0x97, 0x64, 0x02, 0x98, + 0x99, 0x00, 0xf1, 0xc7, 0x24, 0x02, 0xc4, 0xdf, + 0x07, 0xf1, 0x17, 0x68, 0x02, 0x94, 0xfe, 0x03, + 0x90, 0xdb, 0x01, 0xbb, 0xec, 0x00, 0xc7, 0x9c, + 0x03, 0xf0, 0x94, 0x07, 0xb8, 0xf9, 0x06, 0xf4, + 0x1b, 0x29, 0xc7, 0xd9, 0x03, 0xb8, 0x9c, 0x06, + 0xf4, 0x0b, 0x20, 0xf1, 0xf7, 0x00, 0x06, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x12, 0xfa, 0xf9, 0x00, + 0xf1, 0xf7, 0x00, 0x07, 0xf0, 0xf3, 0x03, 0xf0, + 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf4, 0x0e, 0x17, + 0x80, 0xea, 0x01, 0x80, 0xe0, 0x00, 0x80, 0x1b, + 0x00, 0xb0, 0xb6, 0x10, 0xf4, 0x1b, 0x08, 0xbd, + 0x94, 0x80, 0x19, 0x00, 0xf1, 0xf7, 0x00, 0x12, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x04, 0xfa, 0xf9, + 0x00, 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, 0xf1, + 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x10, 0xfa, 0xf9, 0x00, 0xf1, 0xd7, 0x1c, 0x02, + 0xf1, 0x97, 0x20, 0x02, 0x98, 0xdf, 0x00, 0x98, + 0x99, 0x00, 0xb8, 0x9f, 0x06, 0xf5, 0x0b, 0x83, + 0x00, 0xf1, 0xe7, 0xdc, 0x01, 0xc4, 0xf9, 0x07, + 0xb6, 0x94, 0x03, 0xbb, 0x9e, 0x00, 0x98, 0x9e, + 0x00, 0x98, 0x9b, 0x01, 0xb6, 0xf0, 0x01, 0xf1, + 0x97, 0xff, 0x87, 0x80, 0xdf, 0x00, 0xff, 0xe9, + 0xa4, 0xb0, 0xf6, 0x10, 0xf4, 0x1b, 0x08, 0xbd, + 0x94, 0x80, 0xd9, 0x00, 0xb0, 0xa6, 0x05, 0xf4, + 0x0b, 0x32, 0xb0, 0xa6, 0x05, 0xf4, 0x0c, 0x0d, + 0xb0, 0xa6, 0x04, 0xf5, 0x1b, 0x41, 0x00, 0xf4, + 0x0e, 0x1b, 0xf0, 0x97, 0x02, 0xf0, 0x93, 0x01, + 0xb8, 0xa9, 0x06, 0xf4, 0x0b, 0x2a, 0xb6, 0x90, + 0x01, 0xb8, 0xa9, 0x06, 0xf4, 0x1b, 0x28, 0xf4, + 0x0e, 0x29, 0xf5, 0x21, 0xfc, 0x11, 0xf4, 0x0e, + 0x22, 0xf5, 0x21, 0xe7, 0x06, 0xf1, 0xf7, 0x00, + 0x02, 0xf0, 0xf3, 0x03, 0xf0, 0x97, 0x04, 0xfa, + 0xf9, 0x00, 0xf4, 0x0e, 0x0e, 0xf5, 0x21, 0x90, + 0x1b, 0xf4, 0x0e, 0x07, 0xf5, 0x21, 0x05, 0x1e, + 0xf1, 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x10, 0xfa, 0xf9, 0x00, 0xf8, 0x00, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x0b, 0xf0, 0xf3, 0x02, + 0x92, 0xa0, 0x00, 0xf0, 0x97, 0x20, 0xfa, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x02, 0xf0, 0xf3, 0x03, + 0xf0, 0x97, 0x04, 0xfa, 0xf9, 0x00, 0xf4, 0x0e, + 0x0d, 0xb0, 0x06, 0x00, 0xf4, 0x0b, 0x07, 0xf5, + 0x21, 0x97, 0x1e, 0xf0, 0x97, 0x00, 0xf0, 0x93, + 0x03, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf1, 0x94, + 0x00, 0x20, 0xf4, 0x1b, 0xe7, 0xf1, 0xf7, 0x00, + 0x13, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x20, 0xfa, + 0xf9, 0x00, 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x90, + 0xf9, 0xa0, 0xf9, 0xb0, 0xf9, 0xc0, 0xf9, 0xd0, + 0xf9, 0xe0, 0xf9, 0xf0, 0xfe, 0x8a, 0x01, 0xf9, + 0xa0, 0xf5, 0x21, 0x19, 0x1a, 0xfc, 0xa0, 0xfe, + 0xa8, 0x00, 0xf4, 0x32, 0x02, 0xfc, 0xf0, 0xfc, + 0xe0, 0xfc, 0xd0, 0xfc, 0xc0, 0xfc, 0xb0, 0xfc, + 0xa0, 0xfc, 0x90, 0xf8, 0x01, 0xf8, 0x00, 0xf9, + 0x00, 0xf1, 0x97, 0x00, 0x0a, 0xf0, 0x93, 0x02, + 0xf9, 0x10, 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x08, + 0xf9, 0x20, 0x92, 0xc1, 0x00, 0xf9, 0x30, 0x92, + 0xa3, 0x00, 0xf9, 0x40, 0xf9, 0x50, 0xf9, 0x60, + 0xf9, 0x70, 0xf9, 0x80, 0x92, 0xb8, 0x00, 0xf4, + 0x30, 0xf4, 0xfa, 0x9f, 0x00, 0xbd, 0xa4, 0xf5, + 0x21, 0xa6, 0x07, 0xf0, 0x97, 0xff, 0xf1, 0x93, + 0xff, 0x3f, 0xff, 0x89, 0x74, 0xb0, 0x16, 0x01, + 0xf4, 0x1b, 0x3b, 0x92, 0x1a, 0x00, 0xf5, 0x21, + 0x47, 0x1f, 0xf1, 0x97, 0x00, 0x1b, 0xf0, 0x93, + 0x02, 0xf0, 0xf7, 0x10, 0xfa, 0x9f, 0x00, 0xf1, + 0xa7, 0x14, 0x8a, 0xf0, 0xa3, 0x40, 0xf0, 0xb7, + 0x10, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, 0x07, 0x26, + 0x05, 0xf9, 0x05, 0xf1, 0xa7, 0x6c, 0xa8, 0xf0, + 0xa3, 0x41, 0xf0, 0xb7, 0x10, 0xbd, 0xc4, 0xbd, + 0xd4, 0xf9, 0x05, 0xf1, 0x97, 0x18, 0x00, 0x98, + 0x9a, 0x00, 0xf5, 0x21, 0x12, 0x03, 0xf1, 0x97, + 0x00, 0x1d, 0xf0, 0x93, 0x02, 0xfa, 0x97, 0x00, + 0xf1, 0xf7, 0x00, 0x1e, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x0b, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x00, + 0xf1, 0x93, 0x04, 0x02, 0xb7, 0xf0, 0x00, 0x0c, + 0xfa, 0xf9, 0x00, 0xb0, 0x16, 0x01, 0xf4, 0x1b, + 0x07, 0xf5, 0x21, 0xfa, 0x07, 0xbd, 0xa4, 0xf1, + 0x27, 0x5f, 0x0d, 0xf9, 0x25, 0xf0, 0x97, 0x01, + 0xf0, 0xf7, 0x02, 0xb0, 0x91, 0x00, 0xb0, 0xf1, + 0x02, 0xb0, 0x91, 0x01, 0xf1, 0xd7, 0x00, 0x04, + 0xc7, 0x8e, 0x3c, 0x94, 0x8a, 0x04, 0xf1, 0xb7, + 0x00, 0x02, 0xf0, 0xc7, 0x03, 0xf5, 0x21, 0xb7, + 0x00, 0xf1, 0x97, 0x00, 0x04, 0xf1, 0x17, 0xb0, + 0x01, 0x98, 0x9e, 0x05, 0x98, 0x1d, 0x00, 0x98, + 0x99, 0x04, 0xf1, 0xf7, 0x00, 0xf0, 0xb6, 0xe4, + 0x18, 0xfd, 0x9f, 0x04, 0xb6, 0x95, 0x08, 0xfd, + 0x9e, 0x05, 0xb8, 0x9d, 0x06, 0xf4, 0x0b, 0x2a, + 0x92, 0x9b, 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, + 0xa3, 0x41, 0xbd, 0xc4, 0xbd, 0xd4, 0x80, 0x19, + 0x00, 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, + 0xa7, 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, + 0x13, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0x98, + 0x1a, 0x00, 0xf9, 0x25, 0xf5, 0x21, 0x6f, 0x06, + 0xf0, 0xa7, 0x08, 0xf5, 0x21, 0x98, 0x05, 0xbd, + 0xa4, 0xf5, 0x21, 0x53, 0x07, 0x92, 0x3a, 0x00, + 0x92, 0x8b, 0x00, 0xf0, 0xc7, 0x02, 0xf5, 0x21, + 0x76, 0x0d, 0xf0, 0xa7, 0x01, 0xf5, 0x21, 0x34, + 0x02, 0xf0, 0xa7, 0x02, 0xf5, 0x21, 0xf0, 0x01, + 0xf1, 0x97, 0x00, 0x05, 0x98, 0x99, 0x0f, 0xf1, + 0xf7, 0x90, 0x01, 0xf0, 0x94, 0x07, 0x80, 0xf9, + 0x00, 0xb0, 0x96, 0x01, 0xf5, 0x1b, 0x55, 0x01, + 0xf1, 0xf7, 0x00, 0x1b, 0xf0, 0xf3, 0x02, 0xbd, + 0x94, 0xfa, 0xf9, 0x00, 0xf1, 0xa7, 0x14, 0x8a, + 0xf0, 0xa3, 0x40, 0xbd, 0xb4, 0xbd, 0xc4, 0xbd, + 0xd4, 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf1, 0xa7, 0x6c, 0xa8, 0xf0, + 0xa3, 0x41, 0xbd, 0xb4, 0xf9, 0x05, 0xbd, 0xb4, + 0xf1, 0xa7, 0x08, 0x02, 0xf0, 0xa3, 0x40, 0xf5, + 0x21, 0x18, 0x06, 0xf1, 0xf7, 0x00, 0x07, 0xf0, + 0xf3, 0x02, 0xc4, 0xa9, 0x0f, 0xfa, 0xf9, 0x00, + 0xf1, 0x97, 0x00, 0x07, 0xf0, 0x93, 0x02, 0xc7, + 0xaa, 0x64, 0xfa, 0x9a, 0x00, 0xf1, 0xa7, 0x08, + 0x02, 0xf0, 0xa3, 0x40, 0xf0, 0xb7, 0x04, 0xf1, + 0xb3, 0x00, 0x80, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, + 0x27, 0x40, 0x00, 0xf5, 0x21, 0x26, 0x05, 0xf1, + 0x17, 0x48, 0x08, 0xf1, 0xf7, 0x00, 0x05, 0x97, + 0x29, 0x02, 0xb6, 0x94, 0x02, 0xbb, 0x9f, 0x00, + 0x98, 0x9f, 0x00, 0xf1, 0xa7, 0x04, 0x02, 0xf0, + 0xa3, 0x40, 0xbd, 0xc4, 0xbd, 0xd4, 0xc7, 0xf9, + 0x44, 0xb6, 0x94, 0x03, 0xc4, 0xfe, 0x07, 0xfd, + 0xe9, 0x05, 0xc7, 0xf9, 0x50, 0xb6, 0x94, 0x0c, + 0xfd, 0xe9, 0x05, 0xc7, 0xf9, 0x58, 0xb6, 0x94, + 0x12, 0xc7, 0xf0, 0x5c, 0xfd, 0xe9, 0x05, 0xb6, + 0x04, 0x15, 0xc7, 0xfb, 0x4c, 0xc7, 0xf9, 0x48, + 0xb6, 0xb4, 0x09, 0xb6, 0x94, 0x06, 0xc7, 0xff, + 0x54, 0xfd, 0xb9, 0x05, 0xb6, 0xf4, 0x0f, 0xfd, + 0xbf, 0x05, 0xfd, 0xb0, 0x05, 0xff, 0xeb, 0xb5, + 0xf1, 0x07, 0x26, 0x05, 0xb6, 0x20, 0x04, 0xf9, + 0x05, 0x92, 0x1b, 0x00, 0xf1, 0xa7, 0x00, 0x02, + 0xf0, 0xa3, 0x40, 0xb6, 0x10, 0x01, 0xbd, 0xc4, + 0xbd, 0xd4, 0xf9, 0x05, 0xb1, 0x16, 0x50, 0x08, + 0xf5, 0x1b, 0x83, 0xff, 0xf1, 0xa7, 0x00, 0x07, + 0xf0, 0xa3, 0x40, 0xbd, 0xb4, 0xf5, 0x21, 0x18, + 0x06, 0xf1, 0x97, 0x7c, 0xfb, 0xf1, 0x93, 0x03, + 0x03, 0xfd, 0xa9, 0x04, 0xf4, 0x1b, 0xe8, 0xf1, + 0xa7, 0x08, 0x02, 0xf0, 0xa3, 0x40, 0xbd, 0xb4, + 0xbd, 0xc4, 0xbd, 0xd4, 0xf5, 0x21, 0x26, 0x05, + 0xf1, 0x97, 0x00, 0x1b, 0xf0, 0x93, 0x02, 0xf0, + 0xf7, 0x10, 0xfa, 0x9f, 0x00, 0xf1, 0xa7, 0x14, + 0x8a, 0xf0, 0xa3, 0x40, 0xf0, 0xb7, 0x10, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf1, 0x07, 0x26, 0x05, 0xf9, + 0x05, 0xf1, 0xa7, 0x6c, 0xa8, 0xf0, 0xa3, 0x41, + 0xf0, 0xb7, 0x10, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, + 0x05, 0xf1, 0x27, 0x00, 0x05, 0xf1, 0x17, 0xcc, + 0x01, 0x98, 0x29, 0x07, 0x98, 0x1f, 0x00, 0xf0, + 0x94, 0x07, 0xb8, 0xf9, 0x06, 0xf4, 0x0b, 0x2a, + 0x92, 0x9b, 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, + 0xa3, 0x41, 0xbd, 0xc4, 0xbd, 0xd4, 0x80, 0x19, + 0x00, 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, + 0xa7, 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, + 0x19, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0x98, + 0x19, 0x00, 0xb0, 0x96, 0x02, 0xf4, 0x1b, 0x3a, + 0xf1, 0xe7, 0xc4, 0x01, 0x98, 0xe9, 0x00, 0x98, + 0x2f, 0x08, 0xb8, 0x9f, 0x06, 0xf4, 0x0b, 0x2a, + 0x92, 0xfb, 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, + 0xa3, 0x41, 0xbd, 0xc4, 0xbd, 0xd4, 0x80, 0xef, + 0x00, 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, + 0xa7, 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, + 0x17, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xf1, + 0x27, 0x00, 0x05, 0xf1, 0x17, 0xd0, 0x01, 0x98, + 0x29, 0x0a, 0x98, 0x1f, 0x00, 0xf0, 0x94, 0x07, + 0xb8, 0xf9, 0x06, 0xf4, 0x0b, 0x2a, 0x92, 0x9b, + 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, 0xa3, 0x41, + 0xbd, 0xc4, 0xbd, 0xd4, 0x80, 0x19, 0x00, 0xf1, + 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, 0x04, + 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, 0x28, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0x98, 0x19, 0x00, + 0xb0, 0x96, 0x01, 0xf4, 0x1b, 0x3a, 0xf1, 0xe7, + 0xc8, 0x01, 0x98, 0xe9, 0x00, 0x98, 0x2f, 0x0b, + 0xb8, 0x9f, 0x06, 0xf4, 0x0b, 0x2a, 0x92, 0xfb, + 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, 0xa3, 0x41, + 0xbd, 0xc4, 0xbd, 0xd4, 0x80, 0xef, 0x00, 0xf1, + 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, 0x04, + 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, 0x26, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xf1, 0x97, 0x00, + 0x05, 0x98, 0x9f, 0x3f, 0xf1, 0x97, 0xde, 0xc0, + 0xf1, 0x93, 0x0d, 0x60, 0xb8, 0xf9, 0x06, 0xf4, + 0x0b, 0x2e, 0xf1, 0xf7, 0x00, 0x06, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf1, + 0xf7, 0x00, 0x07, 0xf0, 0xf3, 0x03, 0xfa, 0xf9, + 0x00, 0xf5, 0x21, 0x2c, 0x0d, 0xf0, 0xf7, 0x00, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x02, 0xfa, 0xf9, + 0x00, 0xf5, 0x0e, 0x8a, 0x00, 0xf1, 0xf7, 0x00, + 0x05, 0xf0, 0xf3, 0x02, 0xbd, 0x94, 0xfa, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x05, 0xf0, 0xf3, 0x01, + 0xfa, 0xf9, 0x00, 0xf1, 0xa7, 0x00, 0xa8, 0xf0, + 0xa3, 0x41, 0xbd, 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, + 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, + 0x00, 0xa5, 0xf0, 0xa3, 0x41, 0x92, 0x8b, 0x00, + 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xf1, 0xa7, + 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, 0x02, + 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xf1, 0x97, + 0x00, 0x03, 0x98, 0x9f, 0x3f, 0xf1, 0x97, 0xab, + 0xec, 0xf1, 0x93, 0x0b, 0xad, 0xb8, 0xf9, 0x06, + 0xf5, 0x0b, 0x42, 0x00, 0xf1, 0xf7, 0x00, 0x06, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x01, 0xfa, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x07, 0xf0, 0xf3, 0x03, + 0xfa, 0xf9, 0x00, 0xf0, 0xf7, 0x00, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x02, 0xfa, 0xf9, 0x00, 0xf5, + 0x21, 0x2c, 0x0d, 0xf1, 0xf7, 0x00, 0x09, 0xf0, + 0xf3, 0x01, 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xf1, + 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf5, 0x0e, + 0x2c, 0x03, 0xf1, 0x97, 0x18, 0x00, 0x98, 0x9a, + 0x00, 0xf5, 0x21, 0x12, 0x03, 0xf1, 0xf7, 0xfc, + 0x4a, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x0c, 0xfa, + 0xf9, 0x00, 0xf5, 0x21, 0x57, 0x04, 0xf1, 0xf7, + 0xfc, 0x47, 0xf0, 0xf3, 0x02, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf0, 0x97, 0x04, 0xb7, 0xf0, 0x00, + 0x03, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0xcb, 0x00, + 0xb7, 0xf2, 0xfc, 0x77, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0x00, 0x03, 0x98, 0x99, 0x03, 0xb7, 0xf2, + 0x00, 0x12, 0xf1, 0x94, 0xff, 0xff, 0xfa, 0xf9, + 0x00, 0xf1, 0x97, 0xe8, 0x00, 0x98, 0x9e, 0x00, + 0xf0, 0xa7, 0x02, 0xf0, 0xb7, 0x01, 0x92, 0xac, + 0x00, 0xf1, 0xd7, 0x4c, 0x00, 0xf5, 0x21, 0x24, + 0x13, 0xf1, 0x97, 0xd0, 0x01, 0x98, 0x99, 0x00, + 0xb0, 0x96, 0x01, 0xf5, 0x1b, 0xb0, 0x00, 0xf1, + 0x97, 0xc8, 0x01, 0x98, 0x9a, 0x00, 0xf5, 0x21, + 0x5f, 0x0d, 0xf1, 0xf7, 0x00, 0xd3, 0xf0, 0xf3, + 0x01, 0xf1, 0x97, 0xbe, 0x01, 0xfa, 0xf9, 0x00, + 0xf1, 0x97, 0x00, 0x03, 0x98, 0x99, 0x3a, 0xb7, + 0xf2, 0x00, 0x12, 0xf1, 0x94, 0xff, 0xff, 0xfa, + 0xf9, 0x00, 0xf1, 0x97, 0x6c, 0x01, 0x98, 0x9e, + 0x00, 0xf0, 0xa7, 0x02, 0xf1, 0xd7, 0xec, 0x00, + 0x92, 0xac, 0x00, 0x92, 0xab, 0x00, 0xf5, 0x21, + 0x24, 0x13, 0xf1, 0x97, 0xd8, 0x01, 0x98, 0x9a, + 0x00, 0xf1, 0xb7, 0x68, 0x00, 0xf1, 0x07, 0x00, + 0xd3, 0xf0, 0x03, 0x01, 0xf5, 0x21, 0x1e, 0x34, + 0xfa, 0x0a, 0x00, 0xf1, 0x97, 0x00, 0x03, 0x98, + 0x99, 0x3b, 0xf1, 0xf7, 0x00, 0xc1, 0xf0, 0xf3, + 0x01, 0xf1, 0x94, 0xff, 0xff, 0xfa, 0xf9, 0x00, + 0xf1, 0x97, 0x80, 0x01, 0x98, 0x9e, 0x00, 0xf1, + 0x07, 0x24, 0x13, 0xf0, 0xa7, 0x02, 0xf0, 0xb7, + 0x09, 0xf0, 0xc7, 0x01, 0xf1, 0xd7, 0x70, 0x01, + 0xf9, 0x05, 0xf1, 0x97, 0x88, 0x01, 0x98, 0x9e, + 0x00, 0xf0, 0xa7, 0x02, 0xf0, 0xb7, 0x0a, 0xf0, + 0xc7, 0x04, 0xf1, 0xd7, 0x84, 0x01, 0xf9, 0x05, + 0xf1, 0x97, 0xb0, 0x01, 0x98, 0x9a, 0x00, 0xf5, + 0x21, 0x5f, 0x0d, 0xf5, 0x21, 0x57, 0x04, 0xf1, + 0xf7, 0x00, 0x05, 0x98, 0xf9, 0x3e, 0xb6, 0x90, + 0x01, 0x80, 0xf9, 0x3e, 0xf0, 0x97, 0x00, 0xf0, + 0x93, 0x01, 0xbd, 0xf4, 0xff, 0x9f, 0x9f, 0xf1, + 0x94, 0x00, 0x01, 0xf4, 0x0b, 0xf1, 0xf1, 0x97, + 0x00, 0x05, 0xf0, 0x93, 0x02, 0xff, 0x9f, 0x9f, + 0xb0, 0x96, 0x00, 0xf4, 0x0b, 0x23, 0xf1, 0xf7, + 0x00, 0x09, 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x02, + 0xf0, 0x97, 0x02, 0xfa, 0xf9, 0x00, 0xb7, 0xf0, + 0x00, 0x12, 0xf5, 0x0e, 0xb8, 0x01, 0xbd, 0xa4, + 0xf5, 0x21, 0xa6, 0x07, 0xf1, 0xf7, 0x00, 0x1b, + 0xf0, 0xf3, 0x02, 0xbd, 0x94, 0xfa, 0xf9, 0x00, + 0xf1, 0xa7, 0x14, 0x8a, 0xf0, 0xa3, 0x40, 0xbd, + 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, 0x07, 0x26, + 0x05, 0xf9, 0x05, 0xf1, 0xa7, 0x6c, 0xa8, 0xf0, + 0xa3, 0x41, 0xbd, 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, + 0xf9, 0x05, 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x0d, 0xfa, 0xf9, 0x00, 0xf5, + 0x21, 0x57, 0x04, 0xf5, 0x21, 0x6f, 0x06, 0xbd, + 0xa4, 0xf5, 0x21, 0x53, 0x07, 0xf1, 0x97, 0x00, + 0x1d, 0xf0, 0x93, 0x02, 0xfa, 0x97, 0x00, 0xf1, + 0xf7, 0x00, 0x1e, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x04, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x00, 0xf1, + 0x93, 0x00, 0x07, 0xb7, 0xf0, 0x00, 0x0c, 0xfa, + 0xf9, 0x00, 0xf1, 0xe7, 0x00, 0x05, 0x98, 0xe2, + 0x04, 0xb0, 0x26, 0x00, 0xf5, 0x0b, 0xda, 0x00, + 0x94, 0x29, 0x03, 0xf1, 0xf7, 0x00, 0xff, 0xb6, + 0x90, 0xff, 0xff, 0x9f, 0xf4, 0xf4, 0x1f, 0x06, + 0xb6, 0xf0, 0xff, 0x98, 0xe9, 0x06, 0x98, 0xea, + 0x05, 0x97, 0xf5, 0x08, 0xbd, 0x64, 0xb6, 0x94, + 0x18, 0xb6, 0xa5, 0x08, 0xbd, 0x44, 0xfd, 0xa9, + 0x05, 0xbd, 0x34, 0xf5, 0x21, 0x5f, 0x0d, 0xf5, + 0x0e, 0x60, 0x00, 0xf0, 0x97, 0x02, 0xf0, 0xf7, + 0x01, 0xb0, 0x91, 0x00, 0xb0, 0xf1, 0x01, 0xbd, + 0xa4, 0x92, 0x3b, 0x00, 0xb0, 0x91, 0x02, 0xf0, + 0xc7, 0x06, 0xf1, 0xd7, 0x00, 0x04, 0xbd, 0xe4, + 0x92, 0x60, 0x00, 0xf5, 0x21, 0xb7, 0x00, 0xf1, + 0x17, 0x00, 0x04, 0x98, 0x1a, 0x00, 0x98, 0x1b, + 0x01, 0xbd, 0xc4, 0xbd, 0xd4, 0xb6, 0x10, 0x08, + 0xf5, 0x21, 0x26, 0x05, 0xb6, 0x00, 0x01, 0xb8, + 0x02, 0x06, 0xf4, 0x0b, 0x24, 0xf1, 0x97, 0x00, + 0x05, 0xb8, 0x19, 0x06, 0xf4, 0x1b, 0xdf, 0xb8, + 0x02, 0x06, 0xf4, 0x0b, 0x14, 0xb6, 0x40, 0x01, + 0xb7, 0x30, 0x00, 0x01, 0x92, 0x06, 0x00, 0xb8, + 0x45, 0x06, 0xf5, 0x1e, 0xa1, 0xff, 0xf1, 0x97, + 0xb0, 0x01, 0x98, 0x9a, 0x00, 0xf5, 0x21, 0x5f, + 0x0d, 0xf1, 0x97, 0x00, 0x05, 0xbd, 0xf4, 0xf0, + 0xa7, 0x02, 0x80, 0x9f, 0x04, 0xf5, 0x21, 0x73, + 0x01, 0xf1, 0x97, 0x00, 0x1d, 0xf0, 0x93, 0x02, + 0xfa, 0x97, 0x00, 0xf1, 0xf7, 0x00, 0x1e, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x0d, 0xfa, 0xf9, 0x00, + 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x00, 0x07, 0xb7, + 0xf0, 0x00, 0x0c, 0xfa, 0xf9, 0x00, 0xf5, 0x21, + 0x2c, 0x0d, 0xf1, 0xf7, 0xb0, 0x01, 0x98, 0xff, + 0x00, 0xf0, 0x97, 0x01, 0xf1, 0xe7, 0xbc, 0x01, + 0x80, 0xe9, 0x00, 0xf1, 0x97, 0xb8, 0x01, 0x80, + 0x98, 0x00, 0xf1, 0x97, 0xb4, 0x01, 0x80, 0x9f, + 0x00, 0xf1, 0x97, 0xc0, 0x01, 0xf0, 0xe7, 0x01, + 0xf1, 0xf7, 0x00, 0x0c, 0xf0, 0xf3, 0x01, 0x80, + 0x9e, 0x00, 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xb7, + 0xf2, 0x00, 0x03, 0xfa, 0xf9, 0x00, 0xf0, 0xf7, + 0x00, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x04, 0xfa, + 0xf9, 0x00, 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x08, + 0xb7, 0xf0, 0x00, 0x12, 0xfa, 0xf9, 0x00, 0xf4, + 0x0e, 0x0e, 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x08, + 0xfa, 0xf9, 0x00, 0xbd, 0xa4, 0xf4, 0x30, 0x0c, + 0xfc, 0x80, 0xfc, 0x70, 0xfc, 0x60, 0xfc, 0x50, + 0xfc, 0x40, 0xfc, 0x30, 0xfc, 0x20, 0xfc, 0x10, + 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, + 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0xf9, 0x10, 0xf0, + 0x97, 0x00, 0xf0, 0x93, 0x04, 0xf9, 0x20, 0xf9, + 0x30, 0xf9, 0x40, 0xf9, 0x50, 0x92, 0xb5, 0x00, + 0xf9, 0x60, 0x92, 0xd6, 0x00, 0xf9, 0x70, 0x92, + 0xc7, 0x00, 0xf4, 0x30, 0xf4, 0xfa, 0xf9, 0x00, + 0xf0, 0x97, 0xff, 0xf1, 0x93, 0xff, 0x3f, 0xb0, + 0xd6, 0x00, 0xf0, 0xac, 0x0b, 0xff, 0xb9, 0x34, + 0xf5, 0x21, 0x47, 0x1f, 0xf1, 0xf7, 0x00, 0x1b, + 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x10, 0xfa, 0xf9, + 0x00, 0xf1, 0xa7, 0x14, 0x8a, 0xf0, 0xa3, 0x40, + 0xf0, 0xb7, 0x10, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, + 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, 0x6c, + 0xa8, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, 0x10, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xf1, 0x97, 0x18, + 0x00, 0x98, 0x9a, 0x00, 0xf5, 0x21, 0x12, 0x03, + 0xb0, 0x66, 0x00, 0xf4, 0x0b, 0x32, 0xf1, 0x97, + 0x00, 0x1d, 0xf0, 0x93, 0x02, 0xfa, 0x93, 0x00, + 0xf1, 0xf7, 0x00, 0x1e, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x08, 0xfa, 0xf9, 0x00, 0xf0, 0x97, 0x00, + 0xf1, 0x93, 0x02, 0x05, 0xb7, 0xf0, 0x00, 0x0c, + 0xfa, 0xf9, 0x00, 0xbd, 0x74, 0xf5, 0x21, 0xfa, + 0x07, 0xf5, 0x0e, 0x64, 0x00, 0xb0, 0x76, 0x02, + 0xf4, 0x1b, 0x29, 0xf1, 0x97, 0x00, 0x1d, 0xf0, + 0x93, 0x02, 0xfa, 0x93, 0x00, 0xf1, 0xf7, 0x00, + 0x1e, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x09, 0xfa, + 0xf9, 0x00, 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x03, + 0x04, 0xb7, 0xf0, 0x00, 0x0c, 0xf5, 0x0e, 0xc3, + 0x04, 0xf1, 0x97, 0x00, 0x1d, 0xf0, 0x93, 0x02, + 0xfa, 0x93, 0x00, 0xf1, 0xf7, 0x00, 0x1e, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x0a, 0xfa, 0xf9, 0x00, + 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x02, 0x05, 0xb7, + 0xf0, 0x00, 0x0c, 0xf5, 0x0e, 0x9d, 0x04, 0xf1, + 0x97, 0xb8, 0x01, 0x98, 0x99, 0x00, 0xb8, 0x95, + 0x06, 0xf5, 0x0b, 0xa2, 0x00, 0xbd, 0xa4, 0xf1, + 0x27, 0x5f, 0x0d, 0xf9, 0x25, 0xf0, 0x97, 0x01, + 0xf0, 0xd7, 0x02, 0xb0, 0x91, 0x00, 0xb0, 0xd1, + 0x02, 0xb0, 0x91, 0x01, 0xf1, 0xd7, 0x00, 0x04, + 0xc7, 0x5e, 0x3c, 0x94, 0x5a, 0x04, 0xf1, 0xb7, + 0x00, 0x02, 0xf0, 0xc7, 0x03, 0xf5, 0x21, 0xb7, + 0x00, 0xf1, 0x97, 0x00, 0x04, 0xf1, 0x17, 0xb0, + 0x01, 0x98, 0x9e, 0x05, 0x98, 0x1d, 0x00, 0x98, + 0x99, 0x04, 0xf1, 0xf7, 0x00, 0xf0, 0xb6, 0xe4, + 0x18, 0xfd, 0x9f, 0x04, 0xb6, 0x95, 0x08, 0xfd, + 0x9e, 0x05, 0xb8, 0x9d, 0x06, 0xf4, 0x0b, 0x2f, + 0x92, 0x9a, 0x00, 0x80, 0x19, 0x00, 0xf9, 0x25, + 0x98, 0x1b, 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, + 0xa3, 0x41, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, 0x07, + 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, 0x04, 0xa5, + 0xf0, 0xa3, 0x41, 0xf0, 0xb7, 0x13, 0xbd, 0xc4, + 0xbd, 0xd4, 0xf9, 0x05, 0x98, 0x1a, 0x00, 0xf1, + 0x97, 0xbc, 0x01, 0xbd, 0xd4, 0x80, 0x9d, 0x00, + 0xf1, 0x97, 0xb8, 0x01, 0x80, 0x9d, 0x00, 0xf1, + 0x97, 0xc0, 0x01, 0x80, 0x9d, 0x00, 0xf9, 0x25, + 0xf4, 0x0e, 0x1b, 0xf1, 0x97, 0xb0, 0x01, 0x98, + 0x9a, 0x00, 0xf5, 0x21, 0x5f, 0x0d, 0xf1, 0x97, + 0xc0, 0x01, 0x98, 0x99, 0x00, 0xb0, 0x96, 0x00, + 0xf4, 0x1b, 0x0a, 0xf0, 0xa7, 0x02, 0xf5, 0x21, + 0x34, 0x02, 0xf1, 0x97, 0x00, 0x05, 0x98, 0x99, + 0x0f, 0xf1, 0xf7, 0x90, 0x01, 0xf0, 0x94, 0x07, + 0x80, 0xf9, 0x00, 0xb0, 0x96, 0x01, 0xf4, 0x1b, + 0x34, 0xf1, 0x07, 0x40, 0x00, 0xf1, 0x17, 0x30, + 0x47, 0xf0, 0x13, 0x50, 0x92, 0x1a, 0x00, 0xbd, + 0xb4, 0xf5, 0x21, 0x18, 0x06, 0x97, 0x09, 0x02, + 0xf1, 0xf7, 0x00, 0x05, 0xb6, 0x94, 0x02, 0xb6, + 0x10, 0x04, 0xbb, 0x9f, 0x00, 0xb6, 0x00, 0x04, + 0x80, 0x9a, 0x00, 0xb1, 0x06, 0x60, 0x00, 0xf4, + 0x1b, 0xdd, 0xf1, 0x47, 0x00, 0x05, 0xf1, 0x27, + 0xcc, 0x01, 0x98, 0x49, 0x07, 0x98, 0x2f, 0x00, + 0xc4, 0x91, 0x07, 0xb8, 0xf1, 0x06, 0xf4, 0x0b, + 0x2a, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, 0xa3, 0x41, + 0x92, 0x1b, 0x00, 0xbd, 0xc4, 0xbd, 0xd4, 0x80, + 0x21, 0x00, 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, + 0xf1, 0xa7, 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, + 0xb7, 0x19, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, + 0x98, 0x29, 0x00, 0xb0, 0x96, 0x02, 0xf4, 0x1b, + 0x3a, 0xf1, 0xe7, 0xc4, 0x01, 0x98, 0xe9, 0x00, + 0x98, 0x4f, 0x08, 0xb8, 0x9f, 0x06, 0xf4, 0x0b, + 0x2a, 0x92, 0xfb, 0x00, 0xf1, 0xa7, 0x00, 0xa5, + 0xf0, 0xa3, 0x41, 0xbd, 0xc4, 0xbd, 0xd4, 0x80, + 0xef, 0x00, 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, + 0xf1, 0xa7, 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, + 0xb7, 0x17, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, + 0xb0, 0x16, 0x00, 0xf4, 0x0b, 0x15, 0xb0, 0x66, + 0x00, 0xf4, 0x0b, 0x0f, 0xf1, 0x97, 0x00, 0x05, + 0xbd, 0xd4, 0x80, 0x9d, 0x08, 0x80, 0x9d, 0x07, + 0xf1, 0x27, 0x00, 0x05, 0xf1, 0x17, 0xd0, 0x01, + 0x98, 0x29, 0x0a, 0x98, 0x1f, 0x00, 0xf0, 0x94, + 0x07, 0xb8, 0xf9, 0x06, 0xf4, 0x0b, 0x2a, 0x92, + 0x9b, 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, 0xa3, + 0x41, 0xbd, 0xc4, 0xbd, 0xd4, 0x80, 0x19, 0x00, + 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, + 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, 0x28, + 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0x98, 0x19, + 0x00, 0xb0, 0x96, 0x01, 0xf4, 0x1b, 0x3a, 0xf1, + 0xe7, 0xc8, 0x01, 0x98, 0xe9, 0x00, 0x98, 0x2f, + 0x0b, 0xb8, 0x9f, 0x06, 0xf4, 0x0b, 0x2a, 0x92, + 0xfb, 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, 0xa3, + 0x41, 0xbd, 0xc4, 0xbd, 0xd4, 0x80, 0xef, 0x00, + 0xf1, 0x07, 0x26, 0x05, 0xf9, 0x05, 0xf1, 0xa7, + 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, 0xb7, 0x26, + 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xf1, 0xf7, + 0x00, 0x05, 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf1, 0xa7, 0x00, 0xa8, 0xf0, 0xa3, + 0x41, 0xbd, 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, + 0x07, 0x26, 0x05, 0xf9, 0x05, 0x92, 0x5b, 0x00, + 0xf1, 0xa7, 0x00, 0xa5, 0xf0, 0xa3, 0x41, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xb0, 0x76, 0x02, + 0xf4, 0x1b, 0x10, 0xf1, 0xa7, 0x04, 0xa5, 0xf0, + 0xa3, 0x41, 0xf0, 0xb7, 0x01, 0xf4, 0x0e, 0x0d, + 0xf1, 0xa7, 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xf0, + 0xb7, 0x08, 0xbd, 0xc4, 0xbd, 0xd4, 0xf9, 0x05, + 0xf1, 0x97, 0x18, 0x00, 0x98, 0x9a, 0x00, 0xf5, + 0x21, 0x12, 0x03, 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x0c, 0xfa, 0xf9, 0x00, + 0xf5, 0x21, 0x57, 0x04, 0xf1, 0xf7, 0xfc, 0x47, + 0xf0, 0xf3, 0x02, 0xbd, 0x94, 0xfa, 0xf9, 0x00, + 0xf0, 0x97, 0x03, 0xb7, 0xf0, 0x00, 0x03, 0xfa, + 0xf9, 0x00, 0xf1, 0x97, 0x00, 0x03, 0x98, 0x99, + 0x03, 0xf1, 0xf7, 0x00, 0xc0, 0xf0, 0xf3, 0x01, + 0xf1, 0x94, 0xff, 0xff, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0xe8, 0x00, 0x98, 0x9e, 0x00, 0xf0, 0xa7, + 0x01, 0xf0, 0xc7, 0x02, 0x92, 0xab, 0x00, 0xf1, + 0xd7, 0x4c, 0x00, 0xf5, 0x21, 0x24, 0x13, 0xf1, + 0x97, 0xd0, 0x01, 0x98, 0x99, 0x00, 0xb0, 0x96, + 0x01, 0xf5, 0x1b, 0x90, 0x00, 0xf5, 0x21, 0x57, + 0x04, 0xf1, 0x97, 0xc8, 0x01, 0x98, 0x9a, 0x00, + 0xf5, 0x21, 0x5f, 0x0d, 0xf1, 0x97, 0x00, 0x03, + 0x98, 0x99, 0x3a, 0xf1, 0xf7, 0x00, 0xc0, 0xf0, + 0xf3, 0x01, 0xf1, 0x94, 0xff, 0xff, 0xfa, 0xf9, + 0x00, 0xf1, 0x97, 0x6c, 0x01, 0x98, 0x9e, 0x00, + 0xf0, 0xb7, 0x02, 0xf0, 0xa7, 0x01, 0x92, 0xbc, + 0x00, 0xf1, 0xd7, 0xec, 0x00, 0xf5, 0x21, 0x24, + 0x13, 0xf1, 0x97, 0x00, 0x03, 0x98, 0x99, 0x3b, + 0xf1, 0xf7, 0x00, 0xc0, 0xf0, 0xf3, 0x01, 0xf1, + 0x94, 0xff, 0xff, 0xfa, 0xf9, 0x00, 0xf1, 0x97, + 0x80, 0x01, 0x98, 0x9e, 0x00, 0xf0, 0xa7, 0x01, + 0xf1, 0x07, 0x24, 0x13, 0x92, 0xac, 0x00, 0xf0, + 0xb7, 0x09, 0xf1, 0xd7, 0x70, 0x01, 0xf9, 0x05, + 0xf1, 0x97, 0x88, 0x01, 0x98, 0x9e, 0x00, 0xf0, + 0xa7, 0x01, 0xf0, 0xb7, 0x0a, 0xf0, 0xc7, 0x04, + 0xf1, 0xd7, 0x84, 0x01, 0xf9, 0x05, 0xf1, 0x97, + 0xb0, 0x01, 0x98, 0x9a, 0x00, 0xf5, 0x21, 0x5f, + 0x0d, 0xf5, 0x21, 0x57, 0x04, 0xf1, 0xe7, 0x00, + 0x05, 0x98, 0xef, 0x3d, 0xf0, 0xa7, 0x01, 0xf1, + 0x97, 0x00, 0x03, 0xf1, 0xd7, 0xab, 0xec, 0xf1, + 0xd3, 0x0b, 0xad, 0xbb, 0xfa, 0x00, 0x80, 0x9d, + 0x3f, 0x80, 0xef, 0x3d, 0xf5, 0x21, 0xb2, 0x01, + 0xf0, 0xa7, 0x02, 0xf5, 0x21, 0x73, 0x01, 0xf0, + 0x97, 0x00, 0xf0, 0x93, 0x01, 0xbd, 0xf4, 0xff, + 0x9f, 0x9f, 0xf1, 0x94, 0x00, 0x01, 0xf4, 0x0b, + 0xf1, 0xf1, 0x97, 0x18, 0x00, 0x98, 0x9a, 0x00, + 0xf5, 0x21, 0x12, 0x03, 0xf5, 0x21, 0xfc, 0x0c, + 0xf1, 0xf7, 0x00, 0x84, 0xf0, 0xf3, 0x02, 0xf0, + 0x97, 0x05, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x00, + 0x84, 0xf0, 0x93, 0x02, 0xbd, 0xf4, 0xff, 0x9f, + 0x9f, 0xb0, 0x96, 0x00, 0xf4, 0x1b, 0xf1, 0xb0, + 0x76, 0x00, 0xf5, 0x1b, 0x7c, 0x00, 0xbd, 0xa4, + 0xf5, 0x21, 0xa6, 0x07, 0xf1, 0xf7, 0x00, 0x1b, + 0xf0, 0xf3, 0x02, 0xbd, 0x94, 0xfa, 0xf9, 0x00, + 0xf1, 0xa7, 0x14, 0x8a, 0xf0, 0xa3, 0x40, 0xbd, + 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, 0xf1, 0x07, 0x26, + 0x05, 0xf9, 0x05, 0xf1, 0xa7, 0x6c, 0xa8, 0xf0, + 0xa3, 0x41, 0xbd, 0xb4, 0xbd, 0xc4, 0xbd, 0xd4, + 0xf9, 0x05, 0xf1, 0xf7, 0xfc, 0x4a, 0xf0, 0xf3, + 0x02, 0xf0, 0x97, 0x0d, 0xfa, 0xf9, 0x00, 0xf5, + 0x21, 0x57, 0x04, 0xf5, 0x21, 0x2c, 0x0d, 0xf5, + 0x21, 0x6f, 0x06, 0xbd, 0xa4, 0xf5, 0x21, 0x53, + 0x07, 0xf1, 0x97, 0x00, 0x1d, 0xf0, 0x93, 0x02, + 0xfa, 0x93, 0x00, 0xf1, 0xf7, 0x00, 0x1e, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x04, 0xfa, 0xf9, 0x00, + 0xf0, 0x97, 0x00, 0xf1, 0x93, 0x00, 0x02, 0xb7, + 0xf0, 0x00, 0x0c, 0xfa, 0xf9, 0x00, 0xf1, 0xf7, + 0x00, 0x0c, 0xf0, 0xf3, 0x01, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x02, + 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf0, 0x97, + 0x00, 0xf0, 0x93, 0x04, 0xb7, 0xf0, 0x00, 0x12, + 0xfa, 0xf9, 0x00, 0xf4, 0x30, 0x0c, 0xfc, 0x70, + 0xfc, 0x60, 0xfc, 0x50, 0xfc, 0x40, 0xfc, 0x30, + 0xfc, 0x20, 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, + 0xfa, 0xf9, 0x00, 0xf5, 0x21, 0xfa, 0x07, 0xf1, + 0x97, 0xbc, 0x01, 0x98, 0x99, 0x00, 0xb0, 0x96, + 0x00, 0xf5, 0x0b, 0x64, 0xfb, 0xf5, 0x0e, 0x52, + 0xfb, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, + 0xf1, 0x97, 0x00, 0x10, 0xfa, 0xf9, 0x00, 0xf1, + 0xf7, 0x00, 0xc2, 0xf0, 0xf3, 0x02, 0xbd, 0x94, + 0xfa, 0xf9, 0x00, 0xbd, 0xc4, 0xf0, 0xd7, 0x01, + 0xf5, 0x21, 0xb4, 0x27, 0xf1, 0x97, 0x20, 0x02, + 0x98, 0x9b, 0x00, 0xf1, 0x97, 0x1c, 0x02, 0x98, + 0x9e, 0x00, 0xf5, 0x0e, 0x56, 0x00, 0xf1, 0xf7, + 0xdc, 0x01, 0xc4, 0xe9, 0x07, 0xb6, 0xe0, 0x01, + 0xb6, 0x94, 0x03, 0xbb, 0x9f, 0x00, 0x98, 0x9f, + 0x00, 0xb0, 0xe6, 0x10, 0xf4, 0x1b, 0x05, 0xbd, + 0xe4, 0xf1, 0x97, 0xff, 0x87, 0xf1, 0xc7, 0x00, + 0xc3, 0xf0, 0xc3, 0x02, 0xff, 0xf9, 0x94, 0xf0, + 0xd7, 0x01, 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x01, + 0xb8, 0x9f, 0x06, 0xf4, 0x0b, 0x1a, 0xf1, 0x97, + 0x1c, 0x02, 0xf1, 0xf7, 0x00, 0x08, 0xf0, 0xf3, + 0x02, 0x80, 0x9e, 0x00, 0xf0, 0x97, 0x02, 0xfa, + 0xf9, 0x00, 0xf4, 0x0e, 0x14, 0xfa, 0xcd, 0x00, + 0xb8, 0xbe, 0x06, 0xf5, 0x1b, 0xab, 0xff, 0xf1, + 0x97, 0x1c, 0x02, 0x80, 0x9e, 0x00, 0xf1, 0xf7, + 0x00, 0xc2, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x01, + 0xfa, 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x12, 0xf0, + 0xf3, 0x02, 0xf1, 0x97, 0x00, 0x10, 0xfa, 0xf9, + 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, 0x00, + 0x0a, 0xf0, 0xf3, 0x02, 0xf9, 0x10, 0xf0, 0x97, + 0x00, 0xf0, 0x93, 0x01, 0xfa, 0xf9, 0x00, 0xf1, + 0x17, 0x00, 0xc0, 0xf0, 0x13, 0x02, 0xbd, 0x94, + 0xff, 0x19, 0xbf, 0xf1, 0xf7, 0x00, 0xc1, 0xf0, + 0xf3, 0x02, 0xff, 0xf9, 0x0f, 0xf0, 0x97, 0x00, + 0xf1, 0x93, 0x00, 0x80, 0x95, 0x0e, 0x1f, 0xff, + 0xb9, 0x94, 0xf5, 0x0b, 0x77, 0x00, 0xf0, 0x97, + 0xff, 0xf1, 0x93, 0xff, 0x3f, 0xff, 0x09, 0xf4, + 0xff, 0xb9, 0x94, 0xb0, 0xe6, 0x00, 0xf4, 0x0b, + 0x3f, 0xb8, 0x9f, 0x06, 0xf5, 0x0b, 0x7f, 0x00, + 0xf1, 0x97, 0xac, 0x01, 0x98, 0x99, 0x00, 0xb0, + 0x96, 0x00, 0xf4, 0x1b, 0x0e, 0xbd, 0xa4, 0xf0, + 0xc7, 0x02, 0xbd, 0xd4, 0xf5, 0x21, 0xb4, 0x27, + 0xfa, 0x10, 0x00, 0xf1, 0x97, 0xac, 0x01, 0x98, + 0x99, 0x00, 0xb0, 0x96, 0x00, 0xf5, 0x1b, 0x56, + 0x00, 0x92, 0x0b, 0x00, 0xf0, 0xc7, 0x02, 0xbd, + 0xa4, 0xf5, 0x0e, 0x46, 0x00, 0xb8, 0x9f, 0x06, + 0xf5, 0x1b, 0x43, 0x00, 0xf1, 0x97, 0xac, 0x01, + 0x98, 0x99, 0x00, 0xb0, 0x96, 0x00, 0xf4, 0x1b, + 0x0d, 0xbd, 0xa4, 0xbd, 0xc4, 0xbd, 0xd4, 0xf5, + 0x21, 0xb4, 0x27, 0xfa, 0x10, 0x00, 0xf4, 0x0e, + 0x25, 0xb0, 0xe6, 0x00, 0xf4, 0x0b, 0x1f, 0xfa, + 0x10, 0x00, 0xf1, 0x97, 0xac, 0x01, 0x98, 0x99, + 0x00, 0xb0, 0x96, 0x00, 0xf4, 0x1b, 0x0f, 0x92, + 0x0b, 0x00, 0xbd, 0xa4, 0xf0, 0xc7, 0x01, 0xf5, + 0x21, 0xc7, 0x1f, 0xf1, 0xf7, 0x00, 0x12, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x00, 0xf0, 0x93, 0x01, + 0xfa, 0xf9, 0x00, 0xfc, 0x10, 0xfc, 0x00, 0xf8, + 0x00, 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x0a, 0xf0, + 0xf3, 0x02, 0xf9, 0x10, 0xf0, 0x97, 0x00, 0xf0, + 0x93, 0x02, 0x92, 0xb1, 0x00, 0xfa, 0xf9, 0x00, + 0xf1, 0x07, 0x00, 0xc0, 0xf0, 0x03, 0x02, 0xbd, + 0xb4, 0xff, 0x0b, 0xbf, 0xbd, 0xa4, 0xf0, 0xc7, + 0x02, 0xbd, 0xd4, 0xf5, 0x21, 0xb4, 0x27, 0xfa, + 0x01, 0x00, 0xf0, 0xc7, 0x02, 0x92, 0x1b, 0x00, + 0xbd, 0xa4, 0xf5, 0x21, 0xc7, 0x1f, 0xf1, 0xf7, + 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf0, 0x97, 0x00, + 0xf0, 0x93, 0x02, 0xfa, 0xf9, 0x00, 0xfc, 0x10, + 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x00, 0xf1, 0xf7, + 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0xf9, 0x10, 0xf0, + 0x97, 0x08, 0xfa, 0xf9, 0x00, 0xf1, 0xb7, 0x1c, + 0x02, 0xf1, 0x97, 0x20, 0x02, 0x98, 0xbf, 0x00, + 0x98, 0x99, 0x00, 0xf1, 0xe7, 0x64, 0x02, 0xf1, + 0xc7, 0x68, 0x02, 0xb8, 0x9f, 0x06, 0xf4, 0x1b, + 0x1b, 0x98, 0xed, 0x00, 0x98, 0xc9, 0x00, 0xb8, + 0x9d, 0x06, 0xf5, 0x1b, 0x49, 0x00, 0xf1, 0xf7, + 0x00, 0x12, 0xf0, 0xf3, 0x02, 0xf5, 0x0e, 0xfd, + 0x02, 0x98, 0xed, 0x00, 0x98, 0xc9, 0x00, 0xb8, + 0x9d, 0x06, 0xf4, 0x1b, 0x31, 0xf1, 0xe7, 0xdc, + 0x01, 0xc4, 0xf9, 0x07, 0xb6, 0x94, 0x03, 0xbb, + 0x9e, 0x00, 0x98, 0x9e, 0x00, 0x98, 0x90, 0x01, + 0xb6, 0xf0, 0x01, 0xf1, 0x97, 0xff, 0x87, 0x80, + 0xbf, 0x00, 0xff, 0xe9, 0x14, 0xb0, 0xf6, 0x10, + 0xf4, 0x1b, 0x3a, 0xbd, 0xf4, 0x80, 0xbf, 0x00, + 0xf4, 0x0e, 0x32, 0xf1, 0xe7, 0x24, 0x02, 0xc4, + 0xd9, 0x07, 0xb6, 0x94, 0x03, 0xbb, 0x9e, 0x00, + 0x98, 0x9f, 0x00, 0x98, 0x90, 0x01, 0xf1, 0x97, + 0xff, 0x87, 0xf1, 0xe7, 0x64, 0x02, 0xff, 0xf9, + 0x14, 0x90, 0xd9, 0x01, 0x80, 0xe9, 0x00, 0xb0, + 0x96, 0x10, 0xf4, 0x1b, 0x08, 0xbd, 0xf4, 0x80, + 0xef, 0x00, 0xb0, 0x16, 0x12, 0xf5, 0x0b, 0x26, + 0x02, 0xb0, 0x16, 0x12, 0xf5, 0x0c, 0x81, 0x00, + 0xb0, 0x16, 0x06, 0xf5, 0x0b, 0xb6, 0x01, 0xb0, + 0x16, 0x06, 0xf4, 0x0c, 0x34, 0xb0, 0x16, 0x02, + 0xf5, 0x0b, 0xf7, 0x00, 0xb0, 0x16, 0x02, 0xf4, + 0x0c, 0x15, 0xb0, 0x16, 0x00, 0xf5, 0x0b, 0x54, + 0x02, 0xb0, 0x16, 0x01, 0xf5, 0x1b, 0x33, 0x02, + 0xf5, 0x0e, 0xd3, 0x00, 0xb0, 0x16, 0x04, 0xf5, + 0x0b, 0x6e, 0x01, 0xb0, 0x16, 0x04, 0xf5, 0x0c, + 0x75, 0x01, 0xf5, 0x0e, 0x49, 0x01, 0xb0, 0x16, + 0x0b, 0xf5, 0x0b, 0x18, 0x01, 0xb0, 0x16, 0x0b, + 0xf4, 0x0c, 0x1c, 0xb0, 0x16, 0x09, 0xf5, 0x0b, + 0x19, 0x01, 0xb0, 0x16, 0x09, 0xf5, 0x0c, 0x20, + 0x01, 0xb0, 0x16, 0x08, 0xf5, 0x1b, 0xfb, 0x01, + 0xf5, 0x0e, 0xb8, 0x00, 0xb0, 0x16, 0x10, 0xf5, + 0x0b, 0x60, 0x01, 0xb0, 0x16, 0x10, 0xf5, 0x0c, + 0x83, 0x01, 0xb0, 0x16, 0x0c, 0xf5, 0x1b, 0xe2, + 0x01, 0xf5, 0x0e, 0xb0, 0x01, 0xb0, 0x16, 0x25, + 0xf5, 0x0b, 0x63, 0x01, 0xb0, 0x16, 0x25, 0xf4, + 0x0c, 0x2d, 0xb0, 0x16, 0x16, 0xf5, 0x0b, 0x48, + 0x01, 0xb0, 0x16, 0x16, 0xf4, 0x0c, 0x0e, 0xb0, + 0x16, 0x14, 0xf5, 0x0d, 0xd7, 0x01, 0xf5, 0x0e, + 0x6f, 0x01, 0xb0, 0x16, 0x19, 0xf5, 0x0d, 0xcc, + 0x01, 0xb0, 0x16, 0x21, 0xf5, 0x1b, 0xab, 0x01, + 0xf5, 0x0e, 0x7a, 0x00, 0xf0, 0x97, 0x00, 0xf0, + 0x93, 0x01, 0xb8, 0x19, 0x06, 0xf5, 0x0b, 0x7f, + 0x01, 0xb8, 0x19, 0x06, 0xf4, 0x0c, 0x15, 0xb0, + 0x16, 0x28, 0xf5, 0x0d, 0xa7, 0x01, 0xb0, 0x16, + 0x29, 0xf5, 0x1b, 0x86, 0x01, 0xf5, 0x0e, 0x2a, + 0x01, 0xf0, 0x97, 0x02, 0xf0, 0x93, 0x01, 0xb8, + 0x19, 0x06, 0xf5, 0x0b, 0x68, 0x01, 0xb8, 0x19, + 0x06, 0xf5, 0x08, 0x88, 0x01, 0xb6, 0x90, 0x01, + 0xb8, 0x19, 0x06, 0xf5, 0x1b, 0x64, 0x01, 0xf5, + 0x0e, 0x7a, 0x01, 0x92, 0x1a, 0x00, 0x92, 0x0b, + 0x00, 0xf0, 0xc7, 0x02, 0xf4, 0x0e, 0x1c, 0x92, + 0x1a, 0x00, 0x92, 0x0b, 0x00, 0xf0, 0xc7, 0x01, + 0xf5, 0x21, 0xc7, 0x1f, 0xf5, 0x0e, 0x5d, 0x01, + 0x92, 0x1a, 0x00, 0x92, 0x0b, 0x00, 0xbd, 0xc4, + 0xbd, 0xd4, 0xf5, 0x21, 0xb4, 0x27, 0xf5, 0x0e, + 0x4b, 0x01, 0x92, 0x0b, 0x00, 0xf1, 0x97, 0x18, + 0x00, 0xf1, 0xa7, 0x00, 0xa5, 0xf0, 0xa3, 0x41, + 0xbd, 0xc4, 0xbd, 0xd4, 0x80, 0x90, 0x00, 0xf1, + 0x07, 0x26, 0x05, 0xf9, 0x05, 0x92, 0x1b, 0x00, + 0xf1, 0xa7, 0x04, 0xa5, 0xf0, 0xa3, 0x41, 0xbd, + 0xc4, 0xbd, 0xd4, 0xf9, 0x05, 0xf5, 0x0e, 0x1c, + 0x01, 0x92, 0x1a, 0x00, 0x92, 0x0b, 0x00, 0xf5, + 0x21, 0xb8, 0x12, 0xf5, 0x0e, 0x0e, 0x01, 0x92, + 0x1a, 0x00, 0x92, 0x0b, 0x00, 0xf5, 0x21, 0x69, + 0x2d, 0xf5, 0x0e, 0x00, 0x01, 0x92, 0x0b, 0x00, + 0xf0, 0xa7, 0x0a, 0xf5, 0x21, 0x01, 0x2f, 0xf5, + 0x0e, 0xf2, 0x00, 0x92, 0x0b, 0x00, 0xf0, 0xa7, + 0x03, 0xf0, 0xc7, 0x01, 0xf5, 0x21, 0x76, 0x0d, + 0xf0, 0xf7, 0x00, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x10, 0xf5, 0x0e, 0xd5, 0x00, 0x92, 0x1a, 0x00, + 0x92, 0x0b, 0x00, 0xf5, 0x21, 0xfc, 0x11, 0xf5, + 0x0e, 0xca, 0x00, 0x92, 0x0b, 0x00, 0xf0, 0xa7, + 0x05, 0xf5, 0x21, 0xe7, 0x06, 0xf5, 0x0e, 0xbc, + 0x00, 0x92, 0x1a, 0x00, 0x92, 0x0b, 0x00, 0xf5, + 0x21, 0x02, 0x06, 0xf5, 0x0e, 0xae, 0x00, 0x92, + 0x1a, 0x00, 0x92, 0x0b, 0x00, 0xf5, 0x21, 0x08, + 0x17, 0xf5, 0x0e, 0xa0, 0x00, 0x92, 0x1a, 0x00, + 0x92, 0x0b, 0x00, 0xf5, 0x21, 0xf5, 0x09, 0xf5, + 0x0e, 0x92, 0x00, 0x92, 0x1a, 0x00, 0x92, 0x0b, + 0x00, 0xf5, 0x21, 0x56, 0x0b, 0xf5, 0x0e, 0x84, + 0x00, 0x92, 0x0b, 0x00, 0xf0, 0xa7, 0x11, 0xf5, + 0x21, 0xd2, 0x14, 0xf5, 0x0e, 0x76, 0x00, 0x92, + 0x1a, 0x00, 0x92, 0x0b, 0x00, 0xf5, 0x21, 0xd1, + 0x10, 0xf5, 0x0e, 0x68, 0x00, 0x92, 0x0b, 0x00, + 0xf0, 0xa7, 0x15, 0xf5, 0x21, 0x76, 0x14, 0xf5, + 0x0e, 0x5a, 0x00, 0xf1, 0x97, 0x8c, 0x01, 0xf0, + 0xe7, 0x01, 0x80, 0x9e, 0x00, 0xf5, 0x0e, 0x4c, + 0x00, 0xf0, 0xf7, 0x01, 0xf1, 0x97, 0xac, 0x01, + 0x80, 0x9f, 0x00, 0xf0, 0xf7, 0x00, 0xf0, 0xf3, + 0x02, 0xf4, 0x0e, 0x32, 0xf5, 0x21, 0x1b, 0x2e, + 0xf1, 0xf7, 0x00, 0xc3, 0xf0, 0xf3, 0x02, 0xf4, + 0x0e, 0x24, 0x92, 0x1a, 0x00, 0x92, 0x0b, 0x00, + 0xf5, 0x21, 0x90, 0x1b, 0xf4, 0x0e, 0x1d, 0xf1, + 0xf7, 0x00, 0x06, 0xf0, 0xf3, 0x02, 0xf0, 0x97, + 0x11, 0xfa, 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x07, + 0xf0, 0xf3, 0x03, 0xf0, 0x97, 0x01, 0xfa, 0xf9, + 0x00, 0xf1, 0xf7, 0x00, 0x01, 0xf0, 0xf3, 0x02, + 0xf0, 0x97, 0x02, 0xfa, 0xf9, 0x00, 0xb7, 0xf0, + 0x00, 0x11, 0xf0, 0x97, 0x08, 0xfa, 0xf9, 0x00, + 0xfc, 0x10, 0xfc, 0x00, 0xf8, 0x00, 0xf9, 0x00, + 0xf1, 0xf7, 0x00, 0x0a, 0xf0, 0xf3, 0x02, 0xf9, + 0x10, 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xf1, + 0x97, 0x8c, 0x01, 0xbd, 0xf4, 0x80, 0x9f, 0x00, + 0xf1, 0xf7, 0x00, 0x12, 0xf0, 0x97, 0x02, 0xfa, + 0xf9, 0x00, 0xf1, 0x97, 0x96, 0x1f, 0xfe, 0x90, + 0x00, 0xf1, 0xf7, 0x00, 0x07, 0xbd, 0x94, 0xfa, + 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x04, 0xf1, 0x97, + 0x04, 0x87, 0xf0, 0x93, 0x00, 0xfa, 0xf9, 0x00, + 0xf1, 0xf7, 0x00, 0x03, 0xf0, 0x97, 0x04, 0xfa, + 0xf9, 0x00, 0xf1, 0xf7, 0x00, 0x01, 0xf0, 0xf3, + 0x01, 0xf1, 0x97, 0x03, 0x20, 0xfa, 0xf9, 0x00, + 0xf1, 0x97, 0x04, 0x20, 0xb6, 0xf0, 0x04, 0xfa, + 0xf9, 0x00, 0xf1, 0x97, 0x0b, 0x20, 0xb6, 0xf0, + 0x04, 0xfa, 0xf9, 0x00, 0xf1, 0x97, 0x0c, 0x20, + 0xb6, 0xf0, 0x14, 0xfa, 0xf9, 0x00, 0xf1, 0xf7, + 0x40, 0x05, 0xf0, 0xf3, 0x03, 0xf1, 0x97, 0x2d, + 0x20, 0xfa, 0xf9, 0x00, 0xf4, 0x31, 0x10, 0xf4, + 0x31, 0x02, 0xf1, 0xf7, 0x00, 0xc0, 0xf0, 0xf3, + 0x01, 0xbd, 0x94, 0xfa, 0xf9, 0x00, 0xb7, 0xf0, + 0x00, 0x01, 0xfa, 0xf9, 0x00, 0xf1, 0x17, 0x18, + 0x06, 0xbd, 0xb4, 0xf1, 0xa7, 0x04, 0x96, 0xf0, + 0xa3, 0x40, 0xf9, 0x15, 0xf0, 0xa4, 0x1f, 0xf1, + 0x07, 0xd4, 0x01, 0xbd, 0xb4, 0x80, 0x0a, 0x00, + 0xf1, 0xa7, 0x04, 0x96, 0xf0, 0xa3, 0x40, 0xf9, + 0x15, 0x98, 0x0f, 0x00, 0xf1, 0x97, 0xd8, 0x01, + 0xc7, 0xaa, 0x90, 0x80, 0x9a, 0x00, 0xf0, 0x97, + 0x01, 0xbb, 0x9f, 0x04, 0xf1, 0xf7, 0x00, 0x03, + 0xf0, 0xf3, 0x01, 0xb6, 0x92, 0x01, 0xfa, 0xf9, + 0x00, 0xb7, 0xf0, 0x00, 0x01, 0xfa, 0xf9, 0x00, + 0xf1, 0xf7, 0x00, 0x09, 0xf0, 0xf3, 0x03, 0xf0, + 0x97, 0xff, 0xfa, 0xf9, 0x00, 0xbd, 0x14, 0xf1, + 0x07, 0x00, 0x28, 0xf0, 0x03, 0x50, 0xf4, 0x0e, + 0x21, 0x92, 0x0a, 0x00, 0xbd, 0xb4, 0xf5, 0x21, + 0x18, 0x06, 0xf1, 0x97, 0x21, 0x43, 0xf1, 0x93, + 0x65, 0x87, 0xb8, 0xa9, 0x06, 0xf4, 0x1b, 0xec, + 0xb6, 0x10, 0x01, 0xb7, 0x00, 0x00, 0x80, 0xf1, + 0x97, 0xd4, 0x01, 0x98, 0x99, 0x00, 0xb8, 0x19, + 0x06, 0xf4, 0x08, 0xd8, 0xf0, 0xf7, 0x00, 0xf0, + 0xf3, 0x02, 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, + 0xf4, 0x28, 0x02, 0xf5, 0x21, 0x54, 0x2f, 0xf1, + 0x97, 0x8c, 0x01, 0x98, 0x99, 0x00, 0xb0, 0x96, + 0x00, 0xf4, 0x1b, 0x20, 0xf4, 0x31, 0x02, 0xf1, + 0x97, 0x20, 0x02, 0x98, 0x9f, 0x00, 0xf1, 0x97, + 0x1c, 0x02, 0x98, 0x99, 0x00, 0xb8, 0xf9, 0x06, + 0xf4, 0x0b, 0xd8, 0xf4, 0x32, 0x02, 0xf4, 0x0e, + 0xd2, 0xf1, 0xf7, 0x00, 0x12, 0xf0, 0xf3, 0x02, + 0xf0, 0x97, 0x01, 0xfa, 0xf9, 0x00, 0xfc, 0x10, + 0xbd, 0xa4, 0xfc, 0x00, 0xf8, 0x00, 0x92, 0xa9, + 0x00, 0x95, 0xaf, 0x10, 0x95, 0xba, 0x10, 0xff, + 0x9a, 0xa1, 0xfd, 0x9b, 0x00, 0xfd, 0xbf, 0x01, + 0xbb, 0xab, 0x00, 0xb6, 0xa4, 0x10, 0xbb, 0xa9, + 0x00, 0xf8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 +}; + +#endif /* NVC0_CTXCTL_H__ */ diff --git a/driver/pscnv/nvc0_fifo.c b/driver/pscnv/nvc0_fifo.c new file mode 100644 index 00000000..2e20e761 --- /dev/null +++ b/driver/pscnv/nvc0_fifo.c @@ -0,0 +1,426 @@ +/* + * Copyright (C) 2010 Christoph Bumiller. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + */ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "nouveau_reg.h" +#include "pscnv_fifo.h" +#include "pscnv_chan.h" + +struct nvc0_fifo_engine { + struct pscnv_fifo_engine base; + spinlock_t lock; + struct pscnv_bo *playlist[2]; + int cur_playlist; + struct pscnv_bo *ctrl_bo; + volatile uint32_t *fifo_ctl; +}; + +#define nvc0_fifo(x) container_of(x, struct nvc0_fifo_engine, base) + +void nvc0_fifo_takedown(struct drm_device *dev); +void nvc0_fifo_irq_handler(struct drm_device *dev, int irq); +int nvc0_fifo_chan_init_ib (struct pscnv_chan *ch, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t ib_start, uint32_t ib_order); +void nvc0_fifo_chan_kill(struct pscnv_chan *ch); + +int nvc0_fifo_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_fifo_engine *res = kzalloc(sizeof *res, GFP_KERNEL); + int i; + + if (!res) { + NV_ERROR(dev, "PFIFO: Couldn't allocate engine!\n"); + return -ENOMEM; + } + + res->base.takedown = nvc0_fifo_takedown; + res->base.chan_kill = nvc0_fifo_chan_kill; + res->base.chan_init_ib = nvc0_fifo_chan_init_ib; + spin_lock_init(&res->lock); + + res->ctrl_bo = pscnv_mem_alloc(dev, 128 * 0x1000, + PSCNV_GEM_CONTIG, 0, 0xf1f03e95); + + if (!res->ctrl_bo) { + NV_ERROR(dev, "PFIFO: Couldn't allocate control area!\n"); + kfree(res); + return -ENOMEM; + } + + res->playlist[0] = pscnv_mem_alloc(dev, 0x1000, PSCNV_GEM_CONTIG, 0, 0x91a71157); + res->playlist[1] = pscnv_mem_alloc(dev, 0x1000, PSCNV_GEM_CONTIG, 0, 0x91a71157); + if (!res->playlist[0] || !res->playlist[1]) { + NV_ERROR(dev, "PFIFO: Couldn't allocate playlists!\n"); + if (res->playlist[0]) + pscnv_mem_free(res->playlist[0]); + if (res->playlist[1]) + pscnv_mem_free(res->playlist[1]); + pscnv_mem_free(res->ctrl_bo); + kfree(res); + return -ENOMEM; + } + dev_priv->vm->map_kernel(res->playlist[0]); + dev_priv->vm->map_kernel(res->playlist[1]); + res->cur_playlist = 0; + + dev_priv->vm->map_user(res->ctrl_bo); + + if (!res->ctrl_bo->map1) { + NV_ERROR(dev, "PFIFO: Couldn't map control area!\n"); + pscnv_mem_free(res->playlist[0]); + pscnv_mem_free(res->playlist[1]); + pscnv_mem_free(res->ctrl_bo); + kfree(res); + return -ENOMEM; + } + res->fifo_ctl = ioremap(pci_resource_start(dev->pdev, 1) + + res->ctrl_bo->map1->start, 128 << 12); + if (!res->fifo_ctl) { + NV_ERROR(dev, "PFIFO: Couldn't ioremap control area!\n"); + pscnv_mem_free(res->playlist[0]); + pscnv_mem_free(res->playlist[1]); + pscnv_mem_free(res->ctrl_bo); + kfree(res); + return -ENOMEM; + } + + nv_wr32(dev, 0x2100, 0xffffffff); /* PFIFO_INTR */ + + nv_wr32(dev, 0x204, 0); + nv_wr32(dev, 0x204, 7); /* PMC.SUBFIFO_ENABLE */ + + nv_wr32(dev, 0x2204, 7); /* PFIFO.SUBFIFO_ENABLE */ + + /* PFIFO.ENG_SUBFIFO_MASK[0 .. 5] */ + nv_wr32(dev, 0x2208, 0xfffffffe); /* PGRAPH on subfifo 0 */ + nv_wr32(dev, 0x220c, 0xfffffffd); /* PVP, PPP, PBSP on subfifo 1 */ + nv_wr32(dev, 0x2210, 0xfffffffd); + nv_wr32(dev, 0x2214, 0xfffffffd); + nv_wr32(dev, 0x2218, 0xfffffffb); /* PCOPY0 on subfifo 2 */ + nv_wr32(dev, 0x221c, 0xfffffffd); /* PCOPY1 on subfifo 1 */ + + for (i = 0; i < 3; ++i) { /* PSUBFIFO[i] */ + nv_wr32(dev, 0x40108 + i * 0x2000, 0xffffffff); /* INTR */ + nv_wr32(dev, 0x4010c + i * 0x2000, 0xffffffff); /* INTR_EN */ + } + + nv_wr32(dev, 0x2200, 1); /* PFIFO.ENABLE */ + + nv_wr32(dev, 0x2254, /* PFIFO.POLL_AREA */ + (1 << 28) | (res->ctrl_bo->map1->start >> 12)); + + dev_priv->fifo = &res->base; + + nouveau_irq_register(dev, 8, nvc0_fifo_irq_handler); + nv_wr32(dev, 0x2140, 0xbfffffff); /* PFIFO_INTR_EN */ + + return 0; +} + +void nvc0_fifo_takedown(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_fifo_engine *fifo = nvc0_fifo(dev_priv->fifo); + nv_wr32(dev, 0x2140, 0); + nouveau_irq_unregister(dev, 8); + /* XXX */ + pscnv_mem_free(fifo->playlist[0]); + pscnv_mem_free(fifo->playlist[1]); + iounmap(fifo->fifo_ctl); + pscnv_mem_free(fifo->ctrl_bo); + kfree(fifo); + dev_priv->fifo = 0; +} + +void nvc0_fifo_playlist_update(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_fifo_engine *fifo = nvc0_fifo(dev_priv->fifo); + int i, pos; + struct pscnv_bo *vo; + fifo->cur_playlist ^= 1; + vo = fifo->playlist[fifo->cur_playlist]; + for (i = 0, pos = 0; i < 128; i++) { + if (nv_rd32(dev, 0x3004 + i * 8) & 1) { + nv_wv32(vo, pos, i); + nv_wv32(vo, pos + 4, 0x4); + pos += 8; + } + } + dev_priv->vm->bar_flush(dev); + + nv_wr32(dev, 0x2270, vo->start >> 12); + nv_wr32(dev, 0x2274, 0x1f00000 | pos / 8); + + if (!nv_wait(dev, 0x227c, (1 << 20), 0)) + NV_WARN(dev, "WARNING: PFIFO 227c = 0x%08x\n", + nv_rd32(dev, 0x227c)); +} + +void nvc0_fifo_chan_kill(struct pscnv_chan *ch) +{ + struct drm_device *dev = ch->dev; + /* bit 28: active, + * bit 12: loaded, + * bit 0: enabled + */ + uint32_t status; + + status = nv_rd32(dev, 0x3004 + ch->cid * 8); + nv_wr32(dev, 0x3004 + ch->cid * 8, status & ~1); + nv_wr32(dev, 0x2634, ch->cid); + if (!nv_wait(dev, 0x2634, ~0, ch->cid)) + NV_WARN(dev, "WARNING: 2634 = 0x%08x\n", nv_rd32(dev, 0x2634)); + + nvc0_fifo_playlist_update(dev); + + if (nv_rd32(dev, 0x3004 + ch->cid * 8) & 0x1110) { + NV_WARN(dev, "WARNING: PFIFO kickoff fail :(\n"); + } +} + +#define nvchan_wr32(chan, ofst, val) \ + fifo->fifo_ctl[((chan)->cid * 0x1000 + ofst) / 4] = val + +int nvc0_fifo_chan_init_ib (struct pscnv_chan *ch, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t ib_start, uint32_t ib_order) { + struct drm_device *dev = ch->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_fifo_engine *fifo = nvc0_fifo(dev_priv->fifo); + unsigned long irqflags; + + int i; + uint64_t fifo_regs = fifo->ctrl_bo->start + (ch->cid << 12); + + if (ib_order > 29) + return -EINVAL; + + spin_lock_irqsave(&fifo->lock, irqflags); + + for (i = 0x40; i <= 0x50; i += 4) + nvchan_wr32(ch, i, 0); + for (i = 0x58; i <= 0x60; i += 4) + nvchan_wr32(ch, i, 0); + nvchan_wr32(ch, 0x88, 0); + nvchan_wr32(ch, 0x8c, 0); + + for (i = 0; i < 0x100; i += 4) + nv_wv32(ch->bo, i, 0); + + dev_priv->vm->bar_flush(dev); + + nv_wv32(ch->bo, 0x08, fifo_regs); + nv_wv32(ch->bo, 0x0c, fifo_regs >> 32); + + nv_wv32(ch->bo, 0x48, ib_start); /* IB */ + nv_wv32(ch->bo, 0x4c, + (ib_start >> 32) | (ib_order << 16)); + nv_wv32(ch->bo, 0x10, 0xface); + nv_wv32(ch->bo, 0x54, 0x2); + nv_wv32(ch->bo, 0x9c, 0x100); + nv_wv32(ch->bo, 0x84, 0x20400000); + nv_wv32(ch->bo, 0x94, 0x30000000 ^ slimask); + nv_wv32(ch->bo, 0xa4, 0x1f1f1f1f); + nv_wv32(ch->bo, 0xa8, 0x1f1f1f1f); + nv_wv32(ch->bo, 0xac, 0x1f); + nv_wv32(ch->bo, 0x30, 0xfffff902); + /* nv_wv32(chan->vo, 0xb8, 0xf8000000); */ /* previously omitted */ + nv_wv32(ch->bo, 0xf8, 0x10003080); + nv_wv32(ch->bo, 0xfc, 0x10000010); + dev_priv->vm->bar_flush(dev); + + nv_wr32(dev, 0x3000 + ch->cid * 8, 0xc0000000 | ch->bo->start >> 12); + nv_wr32(dev, 0x3004 + ch->cid * 8, 0x1f0001); + + nvc0_fifo_playlist_update(dev); + + spin_unlock_irqrestore(&fifo->lock, irqflags); + + dev_priv->engines[PSCNV_ENGINE_GRAPH]-> + chan_alloc(dev_priv->engines[PSCNV_ENGINE_GRAPH], ch); + dev_priv->engines[PSCNV_ENGINE_COPY0]-> + chan_alloc(dev_priv->engines[PSCNV_ENGINE_COPY0], ch); + dev_priv->engines[PSCNV_ENGINE_COPY1]-> + chan_alloc(dev_priv->engines[PSCNV_ENGINE_COPY1], ch); + + return 0; +} + +static const char *pgf_unit_str(int unit) +{ + switch (unit) { + case 0x0: return "PGRAPH"; + case 0x3: return "PEEPHOLE"; + case 0x4: return "FB BAR (BAR1)"; + case 0x5: return "RAMIN BAR (BAR3)"; + case 0x7: return "PUSHBUF (PFIFO)"; + case 0x10: return "PBSP"; + case 0x11: return "PPPP"; + case 0x13: return "PCOUNTER"; + case 0x14: return "PVP"; + case 0x15: return "PCOPY0"; + case 0x16: return "PCOPY1"; + case 0x17: return "PDAEMON"; + default: + break; + } + return "(unknown unit)"; +} + +static const char *pgf_cause_str(uint32_t flags) +{ + switch (flags & 0xf) { + case 0x0: return "PDE not present"; + case 0x1: return "PT too short"; + case 0x2: return "PTE not present"; + case 0x3: return "LIMIT exceeded"; + case 0x5: return "NOUSER"; + case 0x6: return "PTE set read-only"; + default: + break; + } + return "unknown cause"; +} + +void nvc0_pfifo_page_fault(struct drm_device *dev, int unit) +{ + uint64_t virt; + uint32_t chan, flags; + + chan = nv_rd32(dev, 0x2800 + unit * 0x10) << 12; + virt = nv_rd32(dev, 0x2808 + unit * 0x10); + virt = (virt << 32) | nv_rd32(dev, 0x2804 + unit * 0x10); + flags = nv_rd32(dev, 0x280c + unit * 0x10); + + NV_INFO(dev, "%s PAGE FAULT at 0x%010llx (%c, %s), ch: %08x\n", + pgf_unit_str(unit), virt, + (flags & 0x80) ? 'w' : 'r', pgf_cause_str(flags), chan); +} + +void nvc0_pfifo_subfifo_fault(struct drm_device *dev, int unit) +{ + int cid = nv_rd32(dev, 0x40120 + unit * 0x2000) & 0x7f; + int status = nv_rd32(dev, 0x40108 + unit * 0x2000); + uint32_t addr = nv_rd32(dev, 0x400c0 + unit * 0x2000); + uint32_t data = nv_rd32(dev, 0x400c4 + unit * 0x2000); + int sub = addr >> 16 & 7; + int mthd = addr & 0x3ffc; + int mode = addr >> 21 & 7; + + if (status & 0x200000) { + NV_INFO(dev, "PSUBFIFO %d ILLEGAL_MTHD: ch %d sub %d mthd %04x%s [mode %d] data %08x\n", unit, cid, sub, mthd, ((addr & 1)?" NI":""), mode, data); + nv_wr32(dev, 0x400c0 + unit * 0x2000, 0x80600008); + nv_wr32(dev, 0x40108 + unit * 0x2000, 0x200000); + status &= ~0x200000; + } + if (status & 0x800000) { + NV_INFO(dev, "PSUBFIFO %d EMPTY_SUBCHANNEL: ch %d sub %d mthd %04x%s [mode %d] data %08x\n", unit, cid, sub, mthd, ((addr & 1)?" NI":""), mode, data); + nv_wr32(dev, 0x400c0 + unit * 0x2000, 0x80600008); + nv_wr32(dev, 0x40108 + unit * 0x2000, 0x800000); + status &= ~0x800000; + } + if (status) { + NV_INFO(dev, "unknown PSUBFIFO INTR: 0x%08x\n", status); + nv_wr32(dev, 0x4010c + unit * 0x2000, nv_rd32(dev, 0x4010c + unit * 0x2000) & ~status); + } +} + +void nvc0_fifo_irq_handler(struct drm_device *dev, int irq) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_fifo_engine *fifo = nvc0_fifo(dev_priv->fifo); + uint32_t status; + unsigned long flags; + + spin_lock_irqsave(&fifo->lock, flags); + status = nv_rd32(dev, 0x2100) & nv_rd32(dev, 0x2140); + + if (status & 1) { + NV_INFO(dev, "PFIFO INTR 1!\n"); + nv_wr32(dev, 0x2100, 1); + status &= ~1; + } + + if (status & 0x10000000) { + uint32_t bits = nv_rd32(dev, 0x259c); + uint32_t units = bits; + + while (units) { + int i = ffs(units) - 1; + units &= ~(1 << i); + nvc0_pfifo_page_fault(dev, i); + } + nv_wr32(dev, 0x259c, bits); /* ack */ + status &= ~0x10000000; + } + + if (status & 0x20000000) { + uint32_t bits = nv_rd32(dev, 0x25a0); + uint32_t units = bits; + while (units) { + int i = ffs(units) - 1; + units &= ~(1 << i); + nvc0_pfifo_subfifo_fault(dev, i); + } + nv_wr32(dev, 0x25a0, bits); /* ack */ + status &= ~0x20000000; + } + + if (status & 0x00000100) { + uint32_t ibpk[2]; + uint32_t data = nv_rd32(dev, 0x400c4); + + ibpk[0] = nv_rd32(dev, 0x40110); + ibpk[1] = nv_rd32(dev, 0x40114); + + NV_INFO(dev, "PFIFO FUCKUP: DATA = 0x%08x\n" + "IB PACKET = 0x%08x 0x%08x\n", data, ibpk[0], ibpk[1]); +// status &= ~0x100; + } + + if (status) { + NV_INFO(dev, "unknown PFIFO INTR: 0x%08x\n", status); + /* disable interrupts */ + nv_wr32(dev, 0x2140, nv_rd32(dev, 0x2140) & ~status); + } + + spin_unlock_irqrestore(&fifo->lock, flags); +} + +uint64_t nvc0_fifo_ctrl_offs(struct drm_device *dev, int cid) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_fifo_engine *fifo = nvc0_fifo(dev_priv->fifo); + return fifo->ctrl_bo->map1->start + cid * 0x1000; +} + +/* patched for gdev. */ +volatile uint32_t +*nvc0_fifo_ctrl_ptr(struct drm_device *dev, struct pscnv_chan *chan) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_fifo_engine *fifo = nvc0_fifo(dev_priv->fifo); + return &fifo->fifo_ctl[chan->cid * 0x1000 / 4]; +} diff --git a/driver/pscnv/nvc0_graph.c b/driver/pscnv/nvc0_graph.c new file mode 100644 index 00000000..16d41801 --- /dev/null +++ b/driver/pscnv/nvc0_graph.c @@ -0,0 +1,1138 @@ +/* + * Copyright (C) 2010 Christoph Bumiller. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice (including the + * next paragraph) shall be included in all copies or substantial + * portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE + * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION + * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION + * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "nouveau_reg.h" +#include "pscnv_engine.h" +#include "pscnv_chan.h" +#include "nvc0_vm.h" +#include "nvc0_graph.h" +#include "nvc0_pgraph.xml.h" +/* + * If you want to use NVIDIA's firmware microcode, activate the macro: + * #define USE_BLOB_UCODE + */ +#ifdef USE_BLOB_UCODE +#include "nvc0_ctxctl.h" +#else +#include "nvc0_grhub.fuc.h" +#include "nvc0_grgpc.fuc.h" +#endif + +struct nvc0_graph_chan { + struct pscnv_bo *grctx; + struct pscnv_mm_node *grctx_vm; +}; + +#define GPC_REG(i, r) (NVC0_PGRAPH_GPC(i) + (r)) +#define TP_REG(i, j, r) (NVC0_PGRAPH_GPC_TP(i, j) + (r)) +#define GPC_BC(n) NVC0_PGRAPH_GPC_BROADCAST_##n +#define CTXCTL(n) NVC0_PGRAPH_CTXCTL_##n +#define BC_CTXCTL(n) NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_##n +#define GPC_CTXCTL(n) NVC0_PGRAPH_GPC_CTXCTL_##n +#define ROPC_REG(i, r) (NVC0_PGRAPH_ROPC(i) + (r)) +#define __TRAP_CLEAR_AND_ENABLE \ + (NVC0_PGRAPH_DISPATCH_TRAP_CLEAR | NVC0_PGRAPH_DISPATCH_TRAP_ENABLE) + +void nvc0_graph_takedown(struct pscnv_engine *eng); +int nvc0_graph_chan_alloc(struct pscnv_engine *eng, struct pscnv_chan *ch); +void nvc0_graph_chan_free(struct pscnv_engine *eng, struct pscnv_chan *ch); +void nvc0_graph_chan_kill(struct pscnv_engine *eng, struct pscnv_chan *ch); +void nvc0_graph_irq_handler(struct drm_device *dev, int irq); +void nvc0_ctxctl_load_fuc(struct drm_device *dev); + +static inline void +nvc0_graph_init_reset(struct drm_device *dev) +{ + nv_wr32(dev, 0x200, nv_rd32(dev, 0x200) & 0xffffefff); + nv_wr32(dev, 0x200, nv_rd32(dev, 0x200) | 0x00001000); +} + +static void +nvc0_graph_init_intr(struct drm_device *dev) +{ + nv_wr32(dev, NVC0_PGRAPH_TRAP, 0xffffffff); + nv_wr32(dev, NVC0_PGRAPH_TRAP_EN, 0xffffffff); + + nv_wr32(dev, NVC0_PGRAPH_TRAP_GPCS, 0xffffffff); + nv_wr32(dev, NVC0_PGRAPH_TRAP_GPCS_EN, 0xffffffff); + nv_wr32(dev, NVC0_PGRAPH_TRAP_ROPCS, 0xffffffff); + nv_wr32(dev, NVC0_PGRAPH_TRAP_ROPCS_EN, 0xffffffff); + + nv_wr32(dev, 0x400054, 0x34ce3464); +} + +static void +nvc0_graph_init_units(struct drm_device *dev) +{ + nv_wr32(dev, CTXCTL(INTR_UP_ENABLE), 0xf0000); + + nv_wr32(dev, NVC0_PGRAPH_DISPATCH_TRAP, 0xc0000000); + nv_wr32(dev, NVC0_PGRAPH_M2MF_TRAP, 0xc0000000); + nv_wr32(dev, NVC0_PGRAPH_CCACHE_TRAP, 0xc0000000); + nv_wr32(dev, NVC0_PGRAPH_UNK6000_TRAP_UNK1, 0xc0000000); + nv_wr32(dev, NVC0_PGRAPH_MACRO_TRAP, 0xc0000000); + nv_wr32(dev, NVC0_PGRAPH_UNK6000_TRAP_UNK0, 0xc0000000); + nv_wr32(dev, NVC0_PGRAPH_UNK5800_TRAP, 0xc0000000); + + nv_wr32(dev, NVC0_PGRAPH_UNK5800_TRAP_UNK44, 0x00ffffff); + + nv_mask(dev, GPC_BC(TP_BROADCAST_L1) + 0xc0, 0, 8); + nv_mask(dev, GPC_BC(TP_BROADCAST_MP) + 0xb4, 0, 0x1000); +} + +static void +nvc0_graph_init_gpc(struct drm_device *dev, struct nvc0_graph_engine *graph) +{ + uint32_t magicgpc918; + uint32_t data[NVC0_TP_MAX / 8]; + uint8_t gpc_tp_count[NVC0_GPC_MAX]; + int i, gpc, tp; + + for (gpc = 0; gpc < graph->gpc_count; gpc++) { + /* the number of TPs per GPC. */ + graph->gpc_tp_count[gpc] = nv_rd32(dev, GPC_REG(gpc, 0x2608)) & 0xffff; + /* the number of total TPs. */ + graph->tp_count += graph->gpc_tp_count[gpc]; + } + + magicgpc918 = DIV_ROUND_UP(0x00800000, graph->tp_count); + + /* + * TP ROP UNKVAL(magic_val) + * 450: 4/0/0/0 2 3 + * 460: 3/4/0/0 4 1 + * 465: 3/4/4/0 4 7 + * 470: 3/3/4/4 5 5 + * 480: 3/4/4/4 6 6 + */ + memset(data, 0x00, sizeof(data)); + memcpy(gpc_tp_count, graph->gpc_tp_count, sizeof(graph->gpc_tp_count)); + for (i = 0, gpc = -1; i < graph->tp_count; i++) { + do { + gpc = (gpc + 1) % graph->gpc_count; + } while (!gpc_tp_count[gpc]); + tp = graph->gpc_tp_count[gpc] - gpc_tp_count[gpc]--; + + data[i / 8] |= tp << ((i % 8) * 4); + } + + /* some unknown broadcast areas. */ + nv_wr32(dev, 0x418980, data[0]); + nv_wr32(dev, 0x418984, data[1]); + nv_wr32(dev, 0x418988, data[2]); + nv_wr32(dev, 0x41898c, data[3]); + + for (gpc = 0; gpc < graph->gpc_count; gpc++) { + nv_wr32(dev, GPC_REG(gpc, 0x0914), + (graph->ropc_count << 8) | graph->gpc_tp_count[gpc]); + nv_wr32(dev, GPC_REG(gpc, 0x0910), + (graph->gpc_count << 16) | graph->tp_count); + nv_wr32(dev, GPC_REG(gpc, 0x0918), magicgpc918); + } + + /* some unknown broadcast areas. */ + nv_wr32(dev, 0x419bd4, magicgpc918); + nv_wr32(dev, 0x4188ac, graph->ropc_count); + + for (gpc = 0; gpc < graph->gpc_count; gpc++) { + nv_wr32(dev, GPC_REG(gpc, 0x0420), 0xc0000000); + nv_wr32(dev, GPC_REG(gpc, 0x0900), 0xc0000000); + nv_wr32(dev, GPC_REG(gpc, 0x1028), 0xc0000000); + nv_wr32(dev, GPC_REG(gpc, 0x0824), 0xc0000000); + for (tp = 0; tp < graph->gpc_tp_count[gpc]; tp++) { + nv_wr32(dev, TP_REG(gpc, tp, 0x508), 0xffffffff); + nv_wr32(dev, TP_REG(gpc, tp, 0x50c), 0xffffffff); + nv_wr32(dev, TP_REG(gpc, tp, 0x224), 0xc0000000); + nv_wr32(dev, TP_REG(gpc, tp, 0x48c), 0xc0000000); + nv_wr32(dev, TP_REG(gpc, tp, 0x084), 0xc0000000); + nv_wr32(dev, TP_REG(gpc, tp, 0x644), 0x1ffffe); + nv_wr32(dev, TP_REG(gpc, tp, 0x64c), 0xf); + } + nv_wr32(dev, GPC_REG(gpc, 0x2c90), 0xffffffff); /* CTXCTL */ + nv_wr32(dev, GPC_REG(gpc, 0x2c94), 0xffffffff); /* CTXCTL */ + } +} + +static void +nvc0_graph_init_ropc(struct drm_device *dev, struct nvc0_graph_engine *graph) +{ + int i; + + for (i = 0; i < graph->ropc_count; ++i) { + nv_wr32(dev, ROPC_REG(i, 0x144), 0xc0000000); + nv_wr32(dev, ROPC_REG(i, 0x070), 0xc0000000); + nv_wr32(dev, NVC0_PGRAPH_ROPC_TRAP(i), 0xffffffff); + nv_wr32(dev, NVC0_PGRAPH_ROPC_TRAP_EN(i), 0xffffffff); + } +} + +static void +nvc0_graph_init_regs(struct drm_device *dev) +{ + nv_wr32(dev, 0x400080, 0x003083c2); + nv_wr32(dev, 0x400088, 0x00006fe7); + nv_wr32(dev, 0x40008c, 0x00000000); + nv_wr32(dev, 0x400090, 0x00000030); + + nv_wr32(dev, NVC0_PGRAPH_INTR_EN, 0x013901f7); + nv_wr32(dev, NVC0_PGRAPH_INTR_DISPATCH_CTXCTL_DOWN, 0x00000100); + nv_wr32(dev, NVC0_PGRAPH_INTR_CTXCTL_DOWN, 0x00000000); + nv_wr32(dev, NVC0_PGRAPH_INTR_EN_CTXCTL_DOWN, 0x00000110); + nv_wr32(dev, NVC0_PGRAPH_TRAP_EN, 0x00000000); + nv_wr32(dev, NVC0_PGRAPH_TRAP_GPCS_EN, 0x00000000); + nv_wr32(dev, NVC0_PGRAPH_TRAP_ROPCS_EN, 0x00000000); + nv_wr32(dev, 0x400124, 0x00000002); + + nv_wr32(dev, 0x4188ac, 0x00000005); +} + +#ifdef USE_BLOB_UCODE +static int +nvc0_graph_start_microcode(struct drm_device *dev, + struct nvc0_graph_engine *graph) +{ + int i, j, cx_num; + + nv_wr32(dev, CTXCTL(CC_SCRATCH_CLEAR(0)), 0xffffffff); + nv_wr32(dev, 0x41a10c, 0); + nv_wr32(dev, 0x40910c, 0); + nv_wr32(dev, BC_CTXCTL(UC_CTRL), BC_CTXCTL(UC_CTRL_START_TRIGGER)); + nv_wr32(dev, CTXCTL(UC_CTRL), CTXCTL(UC_CTRL_START_TRIGGER)); + + if (!nv_wait(dev, CTXCTL(CC_SCRATCH(0)), 0x1, 0x1)) { + NV_ERROR(dev, "PGRAPH: HUB_INIT/GPC_INIT timed out\n"); + return -EBUSY; + } + + nv_wr32(dev, CTXCTL(CC_SCRATCH_CLEAR(0)), 0xffffffff); + nv_wr32(dev, CTXCTL(WRCMD_DATA), 0x7fffffff); + nv_wr32(dev, CTXCTL(WRCMD_CMD), 0x21); + + nv_wr32(dev, CTXCTL(CC_SCRATCH_CLEAR(0)), 0xffffffff); + nv_wr32(dev, CTXCTL(WRCMD_DATA), 0); + nv_wr32(dev, CTXCTL(WRCMD_CMD), 0x10); /* grctx size request */ + if (!nv_wait_neq(dev, CTXCTL(CC_SCRATCH(0)), ~0, 0x0)) { + NV_ERROR(dev, "PGRAPH: GRCTX_SIZE timed out\n"); + return -EBUSY; + } + + graph->grctx_size = nv_rd32(dev, CTXCTL(CC_SCRATCH(0))); + graph->grctx_size = (graph->grctx_size + 0xffff) & ~0xffff; + + nv_wr32(dev, CTXCTL(CC_SCRATCH_CLEAR(0)), 0xffffffff); + nv_wr32(dev, CTXCTL(WRCMD_DATA), 0); + nv_wr32(dev, CTXCTL(WRCMD_CMD), 0x16); + if (!nv_wait_neq(dev, CTXCTL(CC_SCRATCH(0)), ~0, 0x0)) { + NV_ERROR(dev, "PGRAPH: CMD 0x16 timed out\n"); + return -EBUSY; + } + + nv_wr32(dev, CTXCTL(CC_SCRATCH_CLEAR(0)), 0xffffffff); + nv_wr32(dev, CTXCTL(WRCMD_DATA), 0); + nv_wr32(dev, CTXCTL(WRCMD_CMD), 0x25); + if (!nv_wait_neq(dev, CTXCTL(CC_SCRATCH(0)), ~0, 0x0)) { + NV_ERROR(dev, "PGRAPH: CMD 0x25 timed out\n"); + return -EBUSY; + } + + cx_num = nv_rd32(dev, CTXCTL(STRANDS)); + for (i = 0; i < cx_num; ++i) { + nv_wr32(dev, CTXCTL(HOST_IO_INDEX), i); + nv_rd32(dev, CTXCTL(STRAND_SIZE)); + } + + cx_num = nv_rd32(dev, GPC_REG(0, 0x2880)); + for (i = 0; i < graph->gpc_count; ++i) { + for (j = 0; j < cx_num; ++j) { + nv_wr32(dev, GPC_CTXCTL(HOST_IO_INDEX(i)), j); + nv_rd32(dev, GPC_CTXCTL(STRAND_SIZE(i))); + } + } + + return 0; +} + +static int +nvc0_graph_load_ctx(struct drm_device *dev, struct pscnv_bo *vo) +{ + uint32_t inst = vo->start >> 12; + + nv_wr32(dev, CTXCTL(RED_SWITCH), 0x070); + nv_wr32(dev, CTXCTL(RED_SWITCH), 0x770); + nv_wr32(dev, 0x40802c, 1); /* ??? */ + nv_wr32(dev, CTXCTL(CC_SCRATCH_CLEAR(0)), 0x30); + + nv_wr32(dev, CTXCTL(WRCMD_DATA), (0x8 << 28) | inst); + nv_wr32(dev, CTXCTL(WRCMD_CMD), 0x3); + + return 0; +} + +int +nvc0_graph_store_ctx(struct drm_device *dev) +{ + uint32_t inst = nv_rd32(dev, 0x409b00) & 0xfffffff; + + nv_wr32(dev, CTXCTL(CC_SCRATCH_CLEAR(0)), 0x3); + nv_wr32(dev, CTXCTL(WRCMD_DATA), (0x8 << 28) | inst); + nv_wr32(dev, CTXCTL(WRCMD_CMD), 0x9); + + if (!nv_wait(dev, CTXCTL(CC_SCRATCH(0)), ~0, 0x1)) { + NV_ERROR(dev, "PGRAPH: failed to store context\n"); + return -EBUSY; + } + NV_INFO(dev, "PGRAPH: context stored: 0x%08x\n", + nv_rd32(dev, CTXCTL(CC_SCRATCH(0)))); + + return 0; +} + +#else +static void +nvc0_graph_ctxctl_debug_unit(struct drm_device *dev, u32 base) +{ + NV_INFO(dev, "PGRAPH: %06x - done 0x%08x\n", base, + nv_rd32(dev, base + 0x400)); + NV_INFO(dev, "PGRAPH: %06x - stat 0x%08x 0x%08x 0x%08x 0x%08x\n", base, + nv_rd32(dev, base + 0x800), nv_rd32(dev, base + 0x804), + nv_rd32(dev, base + 0x808), nv_rd32(dev, base + 0x80c)); + NV_INFO(dev, "PGRAPH: %06x - stat 0x%08x 0x%08x 0x%08x 0x%08x\n", base, + nv_rd32(dev, base + 0x810), nv_rd32(dev, base + 0x814), + nv_rd32(dev, base + 0x818), nv_rd32(dev, base + 0x81c)); +} + +static void +nvc0_graph_ctxctl_debug(struct drm_device *dev) +{ + u32 gpcnr = nv_rd32(dev, CTXCTL(UNITS)) & 0xffff; + u32 gpc; + + nvc0_graph_ctxctl_debug_unit(dev, CTXCTL(INTR_TRIGGER)); + for (gpc = 0; gpc < gpcnr; gpc++) + nvc0_graph_ctxctl_debug_unit(dev, 0x502000 + (gpc * 0x8000)); +} + +static int +nvc0_graph_start_microcode(struct drm_device *dev, + struct nvc0_graph_engine *graph) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + /* start HUB ucode running, it'll init the GPCs */ + nv_wr32(dev, CTXCTL(CC_SCRATCH(0)), dev_priv->chipset); + nv_wr32(dev, 0x40910c, 0x00000000); + nv_wr32(dev, CTXCTL(UC_CTRL), CTXCTL(UC_CTRL_START_TRIGGER)); + + if (!nv_wait(dev, CTXCTL(CC_SCRATCH(0)), 0x80000000, 0x80000000)) { + NV_ERROR(dev, "PGRAPH: HUB_INIT timed out\n"); + nvc0_graph_ctxctl_debug(dev); + return -EBUSY; + } + graph->grctx_size = nv_rd32(dev, CTXCTL(CC_SCRATCH(1))); + + return 0; +} +#endif + +static void +nvc0_graph_load_microcode(struct drm_device *dev) +{ + int i; + const uint32_t val260 = nv_rd32(dev, 0x260); + + nv_wr32(dev, 0x260, val260 & ~1); + + /* load HUB microcode. */ + nv_wr32(dev, CTXCTL(DATA_INDEX(0)), CTXCTL(DATA_INDEX_WRITE_AUTOINCR)); + for (i = 0; i < sizeof(nvc0_grhub_data) / 4; i++) + nv_wr32(dev, CTXCTL(DATA(0)), ((uint32_t *)nvc0_grhub_data)[i]); + + nv_wr32(dev, CTXCTL(CODE_INDEX), CTXCTL(CODE_INDEX_WRITE_AUTOINCR)); + for (i = 0; i < sizeof(nvc0_grhub_code) / 4; i++) { + if ((i & 0x3f) == 0) + nv_wr32(dev, CTXCTL(CODE_VIRT_ADDR), i >> 6); + nv_wr32(dev, CTXCTL(CODE), ((uint32_t *)nvc0_grhub_code)[i]); + } + + /* load GPC microcode. */ + nv_wr32(dev, BC_CTXCTL(DATA_INDEX(0)), BC_CTXCTL(DATA_INDEX_WRITE_AUTOINCR)); + for (i = 0; i < sizeof(nvc0_grgpc_data) / 4; i++) + nv_wr32(dev, BC_CTXCTL(DATA(0)), ((uint32_t *)nvc0_grgpc_data)[i]); + + nv_wr32(dev, BC_CTXCTL(CODE_INDEX), BC_CTXCTL(CODE_INDEX_WRITE_AUTOINCR)); + for (i = 0; i < sizeof(nvc0_grgpc_code) / 4; i++) { + if ((i & 0x3f) == 0) + nv_wr32(dev, BC_CTXCTL(CODE_VIRT_ADDR), i >> 6); + nv_wr32(dev, BC_CTXCTL(CODE), ((uint32_t *)nvc0_grgpc_code)[i]); + } + + nv_wr32(dev, 0x260, val260); +} + +static int +nvc0_graph_init_ctxctl(struct drm_device *dev, struct nvc0_graph_engine *graph) +{ + nvc0_graph_load_microcode(dev); + nvc0_graph_start_microcode(dev, graph); + + return 0; +} + +static int +nvc0_graph_generate_context(struct drm_device *dev, + struct nvc0_graph_engine *graph, + struct pscnv_chan *chan) +{ +#ifdef USE_BLOB_UCODE + struct drm_nouveau_private *dev_priv = dev->dev_private; +#endif + struct nvc0_graph_chan *grch = chan->engdata[PSCNV_ENGINE_GRAPH]; + int i, ret; + uint32_t *grctx; + + if (graph->grctx_initvals) + return 0; + NV_INFO(dev, "PGRAPH: generating default grctx\n"); + + grctx = kmalloc(graph->grctx_size, GFP_KERNEL); + if (!grctx) + return -ENOMEM; + +#ifdef USE_BLOB_UCODE + nvc0_graph_load_ctx(dev, chan->bo); + nv_wv32(grch->grctx, 0x1c, 1); + nv_wv32(grch->grctx, 0x20, 0); + dev_priv->vm->bar_flush(dev); + nv_wv32(grch->grctx, 0x28, 0); + nv_wv32(grch->grctx, 0x2c, 0); + dev_priv->vm->bar_flush(dev); +#else + nv_wr32(dev, CTXCTL(CC_SCRATCH_CLEAR(0)), 0x80000000); + nv_wr32(dev, CTXCTL(WRCMD_DATA), 0x80000000 | chan->bo->start >> 12); + nv_wr32(dev, CTXCTL(WRCMD_CMD), 0x00000001); + if (!nv_wait(dev, CTXCTL(CC_SCRATCH(0)), 0x80000000, 0x80000000)) { + NV_ERROR(dev, "PGRAPH: HUB_SET_CHAN timeout\n"); + nvc0_graph_ctxctl_debug(dev); + ret = -EBUSY; + goto err; + } +#endif + + ret = nvc0_grctx_construct(dev, graph, chan); + if (ret) + goto err; + +#ifdef USE_BLOB_UCODE + ret = nvc0_graph_store_ctx(dev); + if (ret) + goto err; +#else + nv_wr32(dev, CTXCTL(CC_SCRATCH_CLEAR(0)), 0x80000000); + nv_wr32(dev, CTXCTL(WRCMD_DATA), 0x80000000 | chan->bo->start >> 12); + nv_wr32(dev, CTXCTL(WRCMD_CMD), 0x00000002); + if (!nv_wait(dev, CTXCTL(CC_SCRATCH(0)), 0x80000000, 0x80000000)) { + NV_ERROR(dev, "PGRAPH: HUB_CTX_SAVE timeout\n"); + nvc0_graph_ctxctl_debug(dev); + ret = -EBUSY; + goto err; + } +#endif + + for (i = 0; i < graph->grctx_size / 4; ++i) + grctx[i] = nv_rv32(grch->grctx, i * 4); + + graph->grctx_initvals = grctx; + +#ifdef USE_BLOB_CODE + nv_wr32(dev, 0x104048, nv_rd32(dev, 0x104048) | 3); + nv_wr32(dev, 0x105048, nv_rd32(dev, 0x105048) | 3); + + nv_wv32(grch->grctx, 0xf4, 0); + nv_wv32(grch->grctx, 0xf8, 0); + nv_wv32(grch->grctx, 0x10, 0); /* mmio list size */ + nv_wv32(grch->grctx, 0x14, 0); /* mmio list */ + nv_wv32(grch->grctx, 0x18, 0); + nv_wv32(grch->grctx, 0x1c, 1); + nv_wv32(grch->grctx, 0x20, 0); + nv_wv32(grch->grctx, 0x28, 0); + nv_wv32(grch->grctx, 0x2c, 0); + dev_priv->vm->bar_flush(dev); +#endif + + return 0; + +err: + kfree(grctx); + return ret; +} + +void +nvc0_graph_takedown(struct pscnv_engine *eng) +{ + struct nvc0_graph_engine *graph = NVC0_GRAPH(eng); + + nouveau_irq_unregister(eng->dev, 12); + + pscnv_mem_free(graph->obj19848); + pscnv_mem_free(graph->obj0800c); + pscnv_mem_free(graph->obj08004); + pscnv_mem_free(graph->obj188b8); + pscnv_mem_free(graph->obj188b4); + + if (graph->grctx_initvals) + kfree(graph->grctx_initvals); + + kfree(graph); + + nv_wr32(eng->dev, NVC0_PGRAPH_TRAP_EN, 0); + nv_wr32(eng->dev, NVC0_PGRAPH_INTR_EN, 0); +} + +int +nvc0_graph_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct pscnv_bo *vo; + int i, ret; + struct nvc0_graph_engine *res = kzalloc(sizeof *res, GFP_KERNEL); + + if (!res) { + NV_ERROR(dev, "PGRAPH: Couldn't allocate engine!\n"); + return -ENOMEM; + } + NV_INFO(dev, "PGRAPH: Initializing...\n"); + + dev_priv->engines[PSCNV_ENGINE_GRAPH] = &res->base; + res->base.dev = dev; + res->base.takedown = nvc0_graph_takedown; + res->base.chan_alloc = nvc0_graph_chan_alloc; + res->base.chan_kill = nvc0_graph_chan_kill; + res->base.chan_free = nvc0_graph_chan_free; + spin_lock_init(&res->lock); + + vo = pscnv_mem_alloc(dev, 0x1000, PSCNV_GEM_CONTIG, 0, + NVC0_PGRAPH_GPC_BROADCAST_FFB_UNK34_ADDR); + if (!vo) + return -ENOMEM; + ret = dev_priv->vm->map_kernel(vo); + if (ret) + return ret; + res->obj188b4 = vo; /* PGRAPH_GPC_BROADCAST_FFB_UNK32_ADDR */ + + vo = pscnv_mem_alloc(dev, 0x1000, PSCNV_GEM_CONTIG, 0, + NVC0_PGRAPH_GPC_BROADCAST_FFB_UNK38_ADDR); + if (!vo) + return -ENOMEM; + ret = dev_priv->vm->map_kernel(vo); + if (ret) + return ret; + res->obj188b8 = vo; /* PGRAPH_GPC_BROADCAST_FFB_UNK38_ADDR */ + + for (i = 0; i < 0x1000; i += 4) { + nv_wv32(res->obj188b4, i, 0x10); + nv_wv32(res->obj188b8, i, 0x10); + } + dev_priv->vm->bar_flush(dev); + + vo = pscnv_mem_alloc(dev, 0x2000, PSCNV_GEM_CONTIG | PSCNV_GEM_NOUSER, 0, + NVC0_PGRAPH_CCACHE_HUB2GPC_ADDR); + if (!vo) + return -ENOMEM; + ret = dev_priv->vm->map_kernel(vo); + if (ret) + return ret; + res->obj08004 = vo; /* PGRAPH_CCACHE_HUB2GPC_ADDR */ + + vo = pscnv_mem_alloc(dev, 0x8000, PSCNV_GEM_CONTIG | PSCNV_GEM_NOUSER, 0, + NVC0_PGRAPH_CCACHE_HUB2ESETUP_ADDR); + if (!vo) + return -ENOMEM; + ret = dev_priv->vm->map_kernel(vo); + if (ret) + return ret; + res->obj0800c = vo; /* PGRAPH_CCACHE_HUB2ESETUP_ADDR */ + + vo = pscnv_mem_alloc(dev, 3 << 17, PSCNV_GEM_CONTIG, 0, + GPC_BC(TP_BROADCAST_POLY_POLY2ESETUP)); + if (!vo) + return -ENOMEM; + ret = dev_priv->vm->map_kernel(vo); + if (ret) + return ret; + res->obj19848 = vo; + + nv_wr32(dev, NVC0_PGRAPH_FIFO_CONTROL, + nv_rd32(dev, NVC0_PGRAPH_FIFO_CONTROL) & ~0x00010001); + + nvc0_graph_init_reset(dev); + + res->gpc_count = nv_rd32(dev, CTXCTL(UNITS)) & 0x1f; + res->ropc_count = nv_rd32(dev, CTXCTL(UNITS)) >> 16; + + nv_wr32(dev, NVC0_PGRAPH_GPC_BROADCAST_FFB, 0x00000000); + nv_wr32(dev, 0x4188a4, 0x00000000); /* ??? */ + for (i = 0; i < 4; ++i) + nv_wr32(dev, 0x418888 + i * 4, 0x00000000); /* ??? */ + + nv_wr32(dev, NVC0_PGRAPH_GPC_BROADCAST_FFB_UNK34_ADDR, + res->obj188b4->start >> 8); + nv_wr32(dev, NVC0_PGRAPH_GPC_BROADCAST_FFB_UNK38_ADDR, + res->obj188b4->start >> 8); + + nvc0_graph_init_regs(dev); + + nv_wr32(dev, NVC0_PGRAPH_FIFO_CONTROL, + NVC0_PGRAPH_FIFO_CONTROL_UNK16 | NVC0_PGRAPH_FIFO_CONTROL_PULL); + + nv_wr32(dev, NVC0_PGRAPH_INTR, 0xffffffff); + nv_wr32(dev, NVC0_PGRAPH_INTR_EN, 0xffffffff); + + nvc0_graph_init_units(dev); + nvc0_graph_init_gpc(dev, res); + nvc0_graph_init_ropc(dev, res); + nvc0_graph_init_intr(dev); + + ret = nvc0_graph_init_ctxctl(dev, res); + if (ret) + return ret; + + nouveau_irq_register(dev, 12, nvc0_graph_irq_handler); + + /*XXX: these need figuring out... */ + switch (dev_priv->chipset) { + case 0xc0: + if (res->tp_count == 11) /* 465, 3/4/4/0, 4 */ + res->magic_val = 0x07; + else if (res->tp_count == 14) /* 470, 3/3/4/4, 5 */ + res->magic_val = 0x05; + else if (res->tp_count == 15) /* 480, 3/4/4/4, 6 */ + res->magic_val = 0x06; + break; + case 0xc3: /* 450, 4/0/0/0, 2 */ + res->magic_val = 0x03; + break; + case 0xc4: /* 460, 3/4/0/0, 4 */ + res->magic_val = 0x01; + break; + case 0xc1: /* 2/0/0/0, 1 */ + res->magic_val = 0x01; + break; + case 0xc8: /* 4/4/3/4, 5 */ + res->magic_val = 0x06; + break; + case 0xce: /* 4/4/0/0, 4 */ + res->magic_val = 0x03; + break; + case 0xcf: /* 4/0/0/0, 3 */ + res->magic_val = 0x03; + break; + } + + if (!res->magic_val) { + NV_ERROR(dev, "PGRAPH: unknown config: %d/%d/%d/%d, %d\n", + res->gpc_tp_count[0], res->gpc_tp_count[1], + res->gpc_tp_count[2], res->gpc_tp_count[3], res->ropc_count); + /* use 0xc3's values... */ + res->magic_val = 0x03; + } + + return 0; +} + +/* list of PGRAPH writes put in grctx+0x14, count of writes grctx+0x10 */ +static int +nvc0_graph_create_context_mmio_list(struct pscnv_vspace *vs, + struct nvc0_graph_engine *graph) +{ + struct drm_device *dev = vs->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct pscnv_bo *vo; + int i = 0, gpc, tp, ret; + u32 magic; + + vo = pscnv_mem_alloc(vs->dev, 0x1000, PSCNV_GEM_CONTIG, 0, 0x33101157); + if (!vo) + return -ENOMEM; + nvc0_vs(vs)->mmio_bo = vo; + + ret = dev_priv->vm->map_kernel(nvc0_vs(vs)->mmio_bo); + if (ret) + return ret; + + ret = pscnv_vspace_map(vs, vo, 0x1000, (1ULL << 40) - 1, 0, + &nvc0_vs(vs)->mmio_vm); + if (ret) + return ret; + + i = 0; + nv_wv32(vo, i++ * 4, NVC0_PGRAPH_CCACHE_HUB2GPC_ADDR); + nv_wv32(vo, i++ * 4, nvc0_vs(vs)->obj08004->start >> 8); + + nv_wv32(vo, i++ * 4, NVC0_PGRAPH_CCACHE_HUB2GPC_CONF); + nv_wv32(vo, i++ * 4, 0x80000018); + + nv_wv32(vo, i++ * 4, NVC0_PGRAPH_CCACHE_HUB2ESETUP_ADDR); + nv_wv32(vo, i++ * 4, nvc0_vs(vs)->obj0800c->start >> 8); + + nv_wv32(vo, i++ * 4, NVC0_PGRAPH_CCACHE_HUB2ESETUP_CONF); + nv_wv32(vo, i++ * 4, 0x80000000); + + nv_wv32(vo, i++ * 4, GPC_BC(ESETUP_POLY2ESETUP)); + nv_wv32(vo, i++ * 4, (8 << 28) | (nvc0_vs(vs)->obj19848->start >> 12)); + + nv_wv32(vo, i++ * 4, GPC_BC(TP_BROADCAST_POLY_POLY2ESETUP)); + nv_wv32(vo, i++ * 4, (1 << 28) | (nvc0_vs(vs)->obj19848->start >> 12)); + + nv_wv32(vo, i++ * 4, GPC_BC(CCACHE_HUB2GPC_ADDR)); + nv_wv32(vo, i++ * 4, nvc0_vs(vs)->obj0800c->start >> 8); + + nv_wv32(vo, i++ * 4, NVC0_PGRAPH_GPC_BROADCAST_CCACHE_HUB2GPC_CONF); + nv_wv32(vo, i++ * 4, 0); + + nv_wv32(vo, i++ * 4, NVC0_PGRAPH_GPC_BROADCAST_ESETUP_HUB2ESETUP_ADDR); + nv_wv32(vo, i++ * 4, nvc0_vs(vs)->obj08004->start >> 8); + + nv_wv32(vo, i++ * 4, NVC0_PGRAPH_GPC_BROADCAST_ESETUP_HUB2ESETUP_CONF); + nv_wv32(vo, i++ * 4, 0x80000018); + + magic = 0x02180000; + nv_wv32(vo, i++ * 4, 0x00405830); + nv_wv32(vo, i++ * 4, magic); + for (gpc = 0; gpc < graph->gpc_count; gpc++) { + for (tp = 0; tp < graph->gpc_tp_count[gpc]; tp++, magic += 0x0324) { + u32 reg = 0x504520 + (gpc * 0x8000) + (tp * 0x0800); + nv_wv32(vo, i++ * 4, reg); + nv_wv32(vo, i++ * 4, magic); + } + } + + nvc0_vs(vs)->mmio_count = i / 2; + + return 0; +} + +int +nvc0_graph_chan_alloc(struct pscnv_engine *eng, struct pscnv_chan *chan) +{ + struct drm_device *dev = eng->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_graph_engine *graph = NVC0_GRAPH(eng); + struct nvc0_graph_chan *grch = kzalloc(sizeof *grch, GFP_KERNEL); + int i, ret; + + if (!grch) { + NV_ERROR(dev, "PGRAPH: Couldn't allocate channel !\n"); + return -ENOMEM; + } + + grch->grctx = pscnv_mem_alloc(dev, graph->grctx_size, + PSCNV_GEM_CONTIG | PSCNV_GEM_NOUSER, + 0, 0x93ac0747); + if (!grch->grctx) + return -ENOMEM; + + ret = dev_priv->vm->map_kernel(grch->grctx); + if (ret) { + pscnv_mem_free(grch->grctx); + return ret; + } + + ret = pscnv_vspace_map(chan->vspace, + grch->grctx, 0x1000, (1ULL << 40) - 1, + 0, &grch->grctx_vm); + if (ret) { + pscnv_mem_free(grch->grctx); + return ret; + } + + nv_wv32(chan->bo, 0x210, grch->grctx_vm->start | 4); + nv_wv32(chan->bo, 0x214, grch->grctx_vm->start >> 32); + dev_priv->vm->bar_flush(dev); + + if (!nvc0_vs(chan->vspace)->obj08004) { + ret = pscnv_vspace_map(chan->vspace, graph->obj08004, + 0x1000, (1ULL << 40) - 1, 0, + &nvc0_vs(chan->vspace)->obj08004); + if (ret) + return ret; + + ret = pscnv_vspace_map(chan->vspace, graph->obj0800c, + 0x1000, (1ULL << 40) - 1, 0, + &nvc0_vs(chan->vspace)->obj0800c); + if (ret) + return ret; + + ret = pscnv_vspace_map(chan->vspace, graph->obj19848, + 0x1000, (1ULL << 40) - 1, 0, + &nvc0_vs(chan->vspace)->obj19848); + if (ret) + return ret; + } + + chan->engdata[PSCNV_ENGINE_GRAPH] = grch; + + if (!nvc0_vs(chan->vspace)->mmio_bo) { + ret = nvc0_graph_create_context_mmio_list(chan->vspace, graph); + if (ret) + return ret; + } + + if (!graph->grctx_initvals) + return nvc0_graph_generate_context(dev, graph, chan); + + /* fill in context values generated for 1st context */ + for (i = 0; i < graph->grctx_size / 4; ++i) + nv_wv32(grch->grctx, i * 4, graph->grctx_initvals[i]); + +#ifdef USE_BLOB_UCODE + nv_wv32(grch->grctx, 0xf4, 0); + nv_wv32(grch->grctx, 0xf8, 0); + nv_wv32(grch->grctx, 0x10, nvc0_vs(chan->vspace)->mmio_count); + nv_wv32(grch->grctx, 0x14, nvc0_vs(chan->vspace)->mmio_vm->start); + nv_wv32(grch->grctx, 0x18, nvc0_vs(chan->vspace)->mmio_vm->start >> 32); + nv_wv32(grch->grctx, 0x1c, 1); + nv_wv32(grch->grctx, 0x20, 0); + nv_wv32(grch->grctx, 0x28, 0); + nv_wv32(grch->grctx, 0x2c, 0); +#else + nv_wv32(grch->grctx, 0x00, nvc0_vs(chan->vspace)->mmio_count); + nv_wv32(grch->grctx, 0x04, nvc0_vs(chan->vspace)->mmio_vm->start >> 8); +#endif + dev_priv->vm->bar_flush(dev); + + return 0; +} + +void +nvc0_graph_chan_kill(struct pscnv_engine *eng, struct pscnv_chan *ch) +{ + /* FIXME */ +} + +void +nvc0_graph_chan_free(struct pscnv_engine *eng, struct pscnv_chan *ch) +{ + struct nvc0_graph_chan *grch = ch->engdata[PSCNV_ENGINE_GRAPH]; + struct pscnv_vspace *vs = ch->vspace; + + pscnv_vspace_unmap_node(nvc0_vs(vs)->mmio_vm); + pscnv_mem_free(nvc0_vs(vs)->mmio_bo); + pscnv_vspace_unmap_node(grch->grctx_vm); + pscnv_mem_free(grch->grctx); + + /* don't free memory for obj19848/0800c/08004 here. */ + pscnv_vspace_unmap_node(nvc0_vs(vs)->obj19848); + pscnv_vspace_unmap_node(nvc0_vs(vs)->obj0800c); + pscnv_vspace_unmap_node(nvc0_vs(vs)->obj08004); + + kfree(grch); + ch->engdata[PSCNV_ENGINE_GRAPH] = NULL; +} + +/* IRQ Handler */ + +struct pscnv_enum { + int value; + const char *name; + void *data; +}; + +static const struct pscnv_enum dispatch_errors[] = { + { 3, "INVALID_QUERY_OR_TEXTURE", 0 }, + { 4, "INVALID_VALUE", 0 }, + { 5, "INVALID_ENUM", 0 }, + + { 8, "INVALID_OBJECT", 0 }, + + { 0xb, "INVALID_ADDRESS_ALIGNMENT", 0 }, + { 0xc, "INVALID_BITFIELD", 0 }, + + { 0x10, "RT_DOUBLE_BIND", 0 }, + { 0x11, "RT_TYPES_MISMATCH", 0 }, + { 0x12, "RT_LINEAR_WITH_ZETA", 0 }, + + { 0x1b, "SAMPLER_OVER_LIMIT", 0 }, + { 0x1c, "TEXTURE_OVER_LIMIT", 0 }, + + { 0x21, "Z_OUT_OF_BOUNDS", 0 }, + + { 0x23, "M2MF_OUT_OF_BOUNDS", 0 }, + + { 0x27, "CP_MORE_PARAMS_THAN_SHARED", 0 }, + { 0x28, "CP_NO_REG_SPACE_STRIPED", 0 }, + { 0x29, "CP_NO_REG_SPACE_PACKED", 0 }, + { 0x2a, "CP_NOT_ENOUGH_WARPS", 0 }, + { 0x2b, "CP_BLOCK_SIZE_MISMATCH", 0 }, + { 0x2c, "CP_NOT_ENOUGH_LOCAL_WARPS", 0 }, + { 0x2d, "CP_NOT_ENOUGH_STACK_WARPS", 0 }, + { 0x2e, "CP_NO_BLOCKDIM_LATCH", 0 }, + + { 0x31, "ENG2D_FORMAT_MISMATCH", 0 }, + + { 0x47, "VP_CLIP_OVER_LIMIT", 0 }, + + { 0, NULL, 0 }, +}; + +static const struct pscnv_enum * +pscnv_enum_find(const struct pscnv_enum *list, int val) +{ + for (; list->value != val && list->name; ++list); + return list->name ? list : NULL; +} + +static void +nvc0_graph_trap_handler(struct drm_device *dev, int cid) +{ + uint32_t status = nv_rd32(dev, NVC0_PGRAPH_TRAP); + uint32_t ustatus; + + if (status & NVC0_PGRAPH_TRAP_DISPATCH) { + ustatus = nv_rd32(dev, NVC0_PGRAPH_DISPATCH_TRAP) & 0x7fffffff; + if (ustatus & 0x00000001) { + NV_ERROR(dev, "PGRAPH_TRAP_DISPATCH: ch %d\n", cid); + } + if (ustatus & 0x00000002) { + NV_ERROR(dev, "PGRAPH_TRAP_QUERY: ch %d\n", cid); + } + ustatus &= ~0x00000003; + if (ustatus) + NV_ERROR(dev, "PGRAPH_TRAP_DISPATCH: unknown ustatus " + "%08x on ch %d\n", ustatus, cid); + + nv_wr32(dev, NVC0_PGRAPH_DISPATCH_TRAP, __TRAP_CLEAR_AND_ENABLE); + nv_wr32(dev, NVC0_PGRAPH_TRAP, NVC0_PGRAPH_TRAP_DISPATCH); + status &= ~NVC0_PGRAPH_TRAP_DISPATCH; + } + + if (status & NVC0_PGRAPH_TRAP_M2MF) { + ustatus = nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP) & 0x7fffffff; + if (ustatus & 1) + NV_ERROR(dev, "PGRAPH_TRAP_M2MF_NOTIFY: ch %d " + "%08x %08x %08x %08x\n", cid, + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x04), + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x08), + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x0c), + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x10)); + if (ustatus & 2) + NV_ERROR(dev, "PGRAPH_TRAP_M2MF_IN: ch %d " + "%08x %08x %08x %08x\n", cid, + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x04), + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x08), + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x0c), + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x10)); + if (ustatus & 4) + NV_ERROR(dev, "PGRAPH_TRAP_M2MF_OUT: ch %d " + "%08x %08x %08x %08x\n", cid, + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x04), + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x08), + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x0c), + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP + 0x10)); + ustatus &= ~0x00000007; + if (ustatus) + NV_ERROR(dev, "PGRAPH_TRAP_M2MF: unknown ustatus %08x " + "on ch %d\n", cid, ustatus); + nv_wr32(dev, NVC0_PGRAPH_M2MF_TRAP, __TRAP_CLEAR_AND_ENABLE); + nv_wr32(dev, NVC0_PGRAPH_TRAP, NVC0_PGRAPH_TRAP_M2MF); + status &= ~NVC0_PGRAPH_TRAP_M2MF; + } + + if (status & NVC0_PGRAPH_TRAP_UNK4) { + ustatus = nv_rd32(dev, NVC0_PGRAPH_UNK5800_TRAP); + if (ustatus & (1 << 24)) + NV_ERROR(dev, "PGRAPH_TRAP_SHADERS: VPA fail\n"); + if (ustatus & (1 << 25)) + NV_ERROR(dev, "PGRAPH_TRAP_SHADERS: VPB fail\n"); + if (ustatus & (1 << 26)) + NV_ERROR(dev, "PGRAPH_TRAP_SHADERS: TCP fail\n"); + if (ustatus & (1 << 27)) + NV_ERROR(dev, "PGRAPH_TRAP_SHADERS: TEP fail\n"); + if (ustatus & (1 << 28)) + NV_ERROR(dev, "PGRAPH_TRAP_SHADERS: GP fail\n"); + if (ustatus & (1 << 29)) + NV_ERROR(dev, "PGRAPH_TRAP_SHADERS: FP fail\n"); + NV_ERROR(dev, "PGRAPH_TRAP_SHDERS: ustatus = %08x\n", ustatus); + nv_wr32(dev, NVC0_PGRAPH_UNK5800_TRAP, __TRAP_CLEAR_AND_ENABLE); + nv_wr32(dev, NVC0_PGRAPH_TRAP, NVC0_PGRAPH_TRAP_UNK4); + status &= ~NVC0_PGRAPH_TRAP_UNK4; + } + + if (status & NVC0_PGRAPH_TRAP_MACRO) { + ustatus = nv_rd32(dev, NVC0_PGRAPH_MACRO_TRAP) & 0x7fffffff; + if (ustatus & NVC0_PGRAPH_MACRO_TRAP_TOO_FEW_PARAMS) + NV_ERROR(dev, "PGRAPH_TRAP_MACRO: TOO_FEW_PARAMS %08x\n", + nv_rd32(dev, 0x404424)); + if (ustatus & NVC0_PGRAPH_MACRO_TRAP_TOO_MANY_PARAMS) + NV_ERROR(dev, "PGRAPH_TRAP_MACRO: TOO_MANY_PARAMS %08x\n", + nv_rd32(dev, 0x404424)); + if (ustatus & NVC0_PGRAPH_MACRO_TRAP_ILLEGAL_OPCODE) + NV_ERROR(dev, "PGRAPH_TRAP_MACRO: ILLEGAL_OPCODE %08x\n", + nv_rd32(dev, 0x404424)); + if (ustatus & NVC0_PGRAPH_MACRO_TRAP_DOUBLE_BRANCH) + NV_ERROR(dev, "PGRAPH_TRAP_MACRO: DOUBLE_BRANCH %08x\n", + nv_rd32(dev, 0x404424)); + ustatus &= ~0xf; + if (ustatus) + NV_ERROR(dev, "PGRAPH_TRAP_MACRO: unknown ustatus %08x\n", ustatus); + nv_wr32(dev, NVC0_PGRAPH_MACRO_TRAP, __TRAP_CLEAR_AND_ENABLE); + nv_wr32(dev, NVC0_PGRAPH_TRAP, NVC0_PGRAPH_TRAP_MACRO); + status &= ~NVC0_PGRAPH_TRAP_MACRO; + } + + if (status) { + NV_ERROR(dev, "PGRAPH: unknown trap %08x on ch %d\n", status, cid); + NV_INFO(dev, + "DISPATCH_TRAP = %08x\n" + "M2MF_TRAP = %08x\n" + "CCACHE_TRAP = %08x\n" + "UNK6000_TRAP_UNK0 = %08x\n" + "UNK6000_TRAP_UNK1 = %08x\n" + "MACRO_TRAP = %08x\n" + "UNK5800_TRAP = %08x\n", + nv_rd32(dev, NVC0_PGRAPH_DISPATCH_TRAP), + nv_rd32(dev, NVC0_PGRAPH_M2MF_TRAP), + nv_rd32(dev, NVC0_PGRAPH_CCACHE_TRAP), + nv_rd32(dev, NVC0_PGRAPH_UNK6000_TRAP_UNK0), + nv_rd32(dev, NVC0_PGRAPH_UNK6000_TRAP_UNK1), + nv_rd32(dev, NVC0_PGRAPH_MACRO_TRAP), + nv_rd32(dev, NVC0_PGRAPH_UNK5800_TRAP)); + + nv_wr32(dev, NVC0_PGRAPH_TRAP, status); + } +} + +void nvc0_graph_irq_handler(struct drm_device *dev, int irq) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_graph_engine *graph; + uint32_t status; + unsigned long flags; + uint32_t pgraph, addr, datal, datah, ecode, grcl, subc, mthd; + int cid; +#define PGRAPH_ERROR(name) \ + NV_ERROR(dev, "%s: st %08x ch %d sub %d [%04x] mthd %04x data %08x%08x\n", \ + name, pgraph, cid, subc, grcl, mthd, datah, datal); + + graph = NVC0_GRAPH(dev_priv->engines[PSCNV_ENGINE_GRAPH]); + + spin_lock_irqsave(&graph->lock, flags); + + status = nv_rd32(dev, NVC0_PGRAPH_INTR); + ecode = nv_rd32(dev, NVC0_PGRAPH_DATA_ERROR); + pgraph = nv_rd32(dev, NVC0_PGRAPH_STATUS); + addr = nv_rd32(dev, NVC0_PGRAPH_TRAPPED_ADDR); + mthd = addr & NVC0_PGRAPH_TRAPPED_ADDR_MTHD__MASK; + subc = (addr & NVC0_PGRAPH_TRAPPED_ADDR_SUBCH__MASK) >> + NVC0_PGRAPH_TRAPPED_ADDR_SUBCH__SHIFT; + datal = nv_rd32(dev, NVC0_PGRAPH_TRAPPED_DATA_LOW); + datah = nv_rd32(dev, NVC0_PGRAPH_TRAPPED_DATA_HIGH); + grcl = nv_rd32(dev, NVC0_PGRAPH_DISPATCH_CTX_SWITCH) & 0xffff; + cid = -1; + + if (status & NVC0_PGRAPH_INTR_NOTIFY) { + PGRAPH_ERROR("PGRAPH_NOTIFY"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_NOTIFY); + status &= ~NVC0_PGRAPH_INTR_NOTIFY; + } + if (status & NVC0_PGRAPH_INTR_QUERY) { + PGRAPH_ERROR("PGRAPH_QUERY"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_QUERY); + status &= ~NVC0_PGRAPH_INTR_QUERY; + } + if (status & NVC0_PGRAPH_INTR_SYNC) { + PGRAPH_ERROR("PGRAPH_SYNC"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_SYNC); + status &= ~NVC0_PGRAPH_INTR_SYNC; + } + if (status & NVC0_PGRAPH_INTR_ILLEGAL_MTHD) { + PGRAPH_ERROR("PGRAPH_ILLEGAL_MTHD"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_ILLEGAL_MTHD); + status &= ~NVC0_PGRAPH_INTR_ILLEGAL_MTHD; + } + if (status & NVC0_PGRAPH_INTR_ILLEGAL_CLASS) { + PGRAPH_ERROR("PGRAPH_ILLEGAL_CLASS"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_ILLEGAL_CLASS); + status &= ~NVC0_PGRAPH_INTR_ILLEGAL_CLASS; + } + if (status & NVC0_PGRAPH_INTR_DOUBLE_NOTIFY) { + PGRAPH_ERROR("PGRAPH_DOUBLE_NOITFY"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_DOUBLE_NOTIFY); + status &= ~NVC0_PGRAPH_INTR_DOUBLE_NOTIFY; + } + if (status & NVC0_PGRAPH_INTR_UNK7) { + PGRAPH_ERROR("PGRAPH_UNK7"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_UNK7); + status &= ~NVC0_PGRAPH_INTR_UNK7; + } + if (status & NVC0_PGRAPH_INTR_FIRMWARE_MTHD) { + PGRAPH_ERROR("PGRAPH_FIRMWARE_MTHD"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_FIRMWARE_MTHD); + status &= ~NVC0_PGRAPH_INTR_FIRMWARE_MTHD; + } + if (status & NVC0_PGRAPH_INTR_BUFFER_NOTIFY) { + PGRAPH_ERROR("PGRAPH_BUFFER_NOTIFY"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_BUFFER_NOTIFY); + status &= ~NVC0_PGRAPH_INTR_BUFFER_NOTIFY; + } + if (status & NVC0_PGRAPH_INTR_CTXCTL_UP) { + PGRAPH_ERROR("PGRAPH_CTXCTL_UP"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_CTXCTL_UP); + status &= ~NVC0_PGRAPH_INTR_CTXCTL_UP; + } + if (status & NVC0_PGRAPH_INTR_DATA_ERROR) { + const struct pscnv_enum *ev; + ev = pscnv_enum_find(dispatch_errors, ecode); + if (ev) { + NV_ERROR(dev, "PGRAPH_DATA_ERROR [%s]", ev->name); + PGRAPH_ERROR(""); + } else { + NV_ERROR(dev, "PGRAPH_DATA_ERROR [%x]", ecode); + } + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_DATA_ERROR); + status &= ~NVC0_PGRAPH_INTR_DATA_ERROR; + } + if (status & NVC0_PGRAPH_INTR_TRAP) { + nvc0_graph_trap_handler(dev, cid); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_TRAP); + status &= ~NVC0_PGRAPH_INTR_TRAP; + } + if (status & NVC0_PGRAPH_INTR_SINGLE_STEP) { + PGRAPH_ERROR("PGRAPH_SINGLE_STEP"); + nv_wr32(dev, NVC0_PGRAPH_INTR, NVC0_PGRAPH_INTR_SINGLE_STEP); + status &= ~NVC0_PGRAPH_INTR_SINGLE_STEP; + } + if (status) { + NV_ERROR(dev, "Unknown PGRAPH interrupt(s) %08x\n", status); + PGRAPH_ERROR("PGRAPH"); + nv_wr32(dev, NVC0_PGRAPH_INTR, status); + } + + nv_wr32(dev, NVC0_PGRAPH_FIFO_CONTROL, (1 << 16) | 1); + + spin_unlock_irqrestore(&graph->lock, flags); +} diff --git a/driver/pscnv/nvc0_graph.fuc b/driver/pscnv/nvc0_graph.fuc new file mode 100644 index 00000000..e6b22884 --- /dev/null +++ b/driver/pscnv/nvc0_graph.fuc @@ -0,0 +1,400 @@ +/* fuc microcode util functions for nvc0 PGRAPH + * + * Copyright 2011 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +define(`mmctx_data', `.b32 eval((($2 - 1) << 26) | $1)') +define(`queue_init', `.skip eval((2 * 4) + ((8 * 4) * 2))') + +ifdef(`include_code', ` +// Error codes +define(`E_BAD_COMMAND', 0x01) +define(`E_CMD_OVERFLOW', 0x02) + +// Util macros to help with debugging ucode hangs etc +define(`T_WAIT', 0) +define(`T_MMCTX', 1) +define(`T_STRWAIT', 2) +define(`T_STRINIT', 3) +define(`T_AUTO', 4) +define(`T_CHAN', 5) +define(`T_LOAD', 6) +define(`T_SAVE', 7) +define(`T_LCHAN', 8) +define(`T_LCTXH', 9) + +define(`trace_set', ` + mov $r8 0x83c + shl b32 $r8 6 + clear b32 $r9 + bset $r9 $1 + iowr I[$r8 + 0x000] $r9 // CC_SCRATCH[7] +') + +define(`trace_clr', ` + mov $r8 0x85c + shl b32 $r8 6 + clear b32 $r9 + bset $r9 $1 + iowr I[$r8 + 0x000] $r9 // CC_SCRATCH[7] +') + +// queue_put - add request to queue +// +// In : $r13 queue pointer +// $r14 command +// $r15 data +// +queue_put: + // make sure we have space.. + ld b32 $r8 D[$r13 + 0x0] // GET + ld b32 $r9 D[$r13 + 0x4] // PUT + xor $r8 8 + cmpu b32 $r8 $r9 + bra ne #queue_put_next + mov $r15 E_CMD_OVERFLOW + call #error + ret + + // store cmd/data on queue + queue_put_next: + and $r8 $r9 7 + shl b32 $r8 3 + add b32 $r8 $r13 + add b32 $r8 8 + st b32 D[$r8 + 0x0] $r14 + st b32 D[$r8 + 0x4] $r15 + + // update PUT + add b32 $r9 1 + and $r9 0xf + st b32 D[$r13 + 0x4] $r9 + ret + +// queue_get - fetch request from queue +// +// In : $r13 queue pointer +// +// Out: $p1 clear on success (data available) +// $r14 command +// $r15 data +// +queue_get: + bset $flags $p1 + ld b32 $r8 D[$r13 + 0x0] // GET + ld b32 $r9 D[$r13 + 0x4] // PUT + cmpu b32 $r8 $r9 + bra e #queue_get_done + // fetch first cmd/data pair + and $r9 $r8 7 + shl b32 $r9 3 + add b32 $r9 $r13 + add b32 $r9 8 + ld b32 $r14 D[$r9 + 0x0] + ld b32 $r15 D[$r9 + 0x4] + + // update GET + add b32 $r8 1 + and $r8 0xf + st b32 D[$r13 + 0x0] $r8 + bclr $flags $p1 +queue_get_done: + ret + +// nv_rd32 - read 32-bit value from nv register +// +// In : $r14 register +// Out: $r15 value +// +nv_rd32: + mov $r11 0x728 + shl b32 $r11 6 + mov b32 $r12 $r14 + bset $r12 31 // MMIO_CTRL_PENDING + iowr I[$r11 + 0x000] $r12 // MMIO_CTRL + nv_rd32_wait: + iord $r12 I[$r11 + 0x000] + xbit $r12 $r12 31 + bra ne #nv_rd32_wait + mov $r10 6 // DONE_MMIO_RD + call #wait_doneo + iord $r15 I[$r11 + 0x100] // MMIO_RDVAL + ret + +// nv_wr32 - write 32-bit value to nv register +// +// In : $r14 register +// $r15 value +// +nv_wr32: + mov $r11 0x728 + shl b32 $r11 6 + iowr I[$r11 + 0x200] $r15 // MMIO_WRVAL + mov b32 $r12 $r14 + bset $r12 31 // MMIO_CTRL_PENDING + bset $r12 30 // MMIO_CTRL_WRITE + iowr I[$r11 + 0x000] $r12 // MMIO_CTRL + nv_wr32_wait: + iord $r12 I[$r11 + 0x000] + xbit $r12 $r12 31 + bra ne #nv_wr32_wait + ret + +// (re)set watchdog timer +// +// In : $r15 timeout +// +watchdog_reset: + mov $r8 0x430 + shl b32 $r8 6 + bset $r15 31 + iowr I[$r8 + 0x000] $r15 + ret + +// clear watchdog timer +watchdog_clear: + mov $r8 0x430 + shl b32 $r8 6 + iowr I[$r8 + 0x000] $r0 + ret + +// wait_done{z,o} - wait on FUC_DONE bit to become clear/set +// +// In : $r10 bit to wait on +// +define(`wait_done', ` +$1: + trace_set(T_WAIT); + mov $r8 0x818 + shl b32 $r8 6 + iowr I[$r8 + 0x000] $r10 // CC_SCRATCH[6] = wait bit + wait_done_$1: + mov $r8 0x400 + shl b32 $r8 6 + iord $r8 I[$r8 + 0x000] // DONE + xbit $r8 $r8 $r10 + bra $2 #wait_done_$1 + trace_clr(T_WAIT) + ret +') +wait_done(wait_donez, ne) +wait_done(wait_doneo, e) + +// mmctx_size - determine size of a mmio list transfer +// +// In : $r14 mmio list head +// $r15 mmio list tail +// Out: $r15 transfer size (in bytes) +// +mmctx_size: + clear b32 $r9 + nv_mmctx_size_loop: + ld b32 $r8 D[$r14] + shr b32 $r8 26 + add b32 $r8 1 + shl b32 $r8 2 + add b32 $r9 $r8 + add b32 $r14 4 + cmpu b32 $r14 $r15 + bra ne #nv_mmctx_size_loop + mov b32 $r15 $r9 + ret + +// mmctx_xfer - execute a list of mmio transfers +// +// In : $r10 flags +// bit 0: direction (0 = save, 1 = load) +// bit 1: set if first transfer +// bit 2: set if last transfer +// $r11 base +// $r12 mmio list head +// $r13 mmio list tail +// $r14 multi_stride +// $r15 multi_mask +// +mmctx_xfer: + trace_set(T_MMCTX) + mov $r8 0x710 + shl b32 $r8 6 + clear b32 $r9 + or $r11 $r11 + bra e #mmctx_base_disabled + iowr I[$r8 + 0x000] $r11 // MMCTX_BASE + bset $r9 0 // BASE_EN + mmctx_base_disabled: + or $r14 $r14 + bra e #mmctx_multi_disabled + iowr I[$r8 + 0x200] $r14 // MMCTX_MULTI_STRIDE + iowr I[$r8 + 0x300] $r15 // MMCTX_MULTI_MASK + bset $r9 1 // MULTI_EN + mmctx_multi_disabled: + add b32 $r8 0x100 + + xbit $r11 $r10 0 + shl b32 $r11 16 // DIR + bset $r11 12 // QLIMIT = 0x10 + xbit $r14 $r10 1 + shl b32 $r14 17 + or $r11 $r14 // START_TRIGGER + iowr I[$r8 + 0x000] $r11 // MMCTX_CTRL + + // loop over the mmio list, and send requests to the hw + mmctx_exec_loop: + // wait for space in mmctx queue + mmctx_wait_free: + iord $r14 I[$r8 + 0x000] // MMCTX_CTRL + and $r14 0x1f + bra e #mmctx_wait_free + + // queue up an entry + ld b32 $r14 D[$r12] + or $r14 $r9 + iowr I[$r8 + 0x300] $r14 + add b32 $r12 4 + cmpu b32 $r12 $r13 + bra ne #mmctx_exec_loop + + xbit $r11 $r10 2 + bra ne #mmctx_stop + // wait for queue to empty + mmctx_fini_wait: + iord $r11 I[$r8 + 0x000] // MMCTX_CTRL + and $r11 0x1f + cmpu b32 $r11 0x10 + bra ne #mmctx_fini_wait + mov $r10 2 // DONE_MMCTX + call #wait_donez + bra #mmctx_done + mmctx_stop: + xbit $r11 $r10 0 + shl b32 $r11 16 // DIR + bset $r11 12 // QLIMIT = 0x10 + bset $r11 18 // STOP_TRIGGER + iowr I[$r8 + 0x000] $r11 // MMCTX_CTRL + mmctx_stop_wait: + // wait for STOP_TRIGGER to clear + iord $r11 I[$r8 + 0x000] // MMCTX_CTRL + xbit $r11 $r11 18 + bra ne #mmctx_stop_wait + mmctx_done: + trace_clr(T_MMCTX) + ret + +// Wait for DONE_STRAND +// +strand_wait: + push $r10 + mov $r10 2 + call #wait_donez + pop $r10 + ret + +// unknown - call before issuing strand commands +// +strand_pre: + mov $r8 0x4afc + sethi $r8 0x20000 + mov $r9 0xc + iowr I[$r8] $r9 + call #strand_wait + ret + +// unknown - call after issuing strand commands +// +strand_post: + mov $r8 0x4afc + sethi $r8 0x20000 + mov $r9 0xd + iowr I[$r8] $r9 + call #strand_wait + ret + +// Selects strand set?! +// +// In: $r14 id +// +strand_set: + mov $r10 0x4ffc + sethi $r10 0x20000 + sub b32 $r11 $r10 0x500 + mov $r12 0xf + iowr I[$r10 + 0x000] $r12 // 0x93c = 0xf + mov $r12 0xb + iowr I[$r11 + 0x000] $r12 // 0x928 = 0xb + call #strand_wait + iowr I[$r10 + 0x000] $r14 // 0x93c = + mov $r12 0xa + iowr I[$r11 + 0x000] $r12 // 0x928 = 0xa + call #strand_wait + ret + +// Initialise strand context data +// +// In : $r15 context base +// Out: $r15 context size (in bytes) +// +// Strandset(?) 3 hardcoded currently +// +strand_ctx_init: + trace_set(T_STRINIT) + call #strand_pre + mov $r14 3 + call #strand_set + mov $r10 0x46fc + sethi $r10 0x20000 + add b32 $r11 $r10 0x400 + iowr I[$r10 + 0x100] $r0 // STRAND_FIRST_GENE = 0 + mov $r12 1 + iowr I[$r11 + 0x000] $r12 // STRAND_CMD = LATCH_FIRST_GENE + call #strand_wait + sub b32 $r12 $r0 1 + iowr I[$r10 + 0x000] $r12 // STRAND_GENE_CNT = 0xffffffff + mov $r12 2 + iowr I[$r11 + 0x000] $r12 // STRAND_CMD = LATCH_GENE_CNT + call #strand_wait + call #strand_post + + // read the size of each strand, poke the context offset of + // each into STRAND_{SAVE,LOAD}_SWBASE now, no need to worry + // about it later then. + mov $r8 0x880 + shl b32 $r8 6 + iord $r9 I[$r8 + 0x000] // STRANDS + add b32 $r8 0x2200 + shr b32 $r14 $r15 8 + ctx_init_strand_loop: + iowr I[$r8 + 0x000] $r14 // STRAND_SAVE_SWBASE + iowr I[$r8 + 0x100] $r14 // STRAND_LOAD_SWBASE + iord $r10 I[$r8 + 0x200] // STRAND_SIZE + shr b32 $r10 6 + add b32 $r10 1 + add b32 $r14 $r10 + add b32 $r8 4 + sub b32 $r9 1 + bra ne #ctx_init_strand_loop + + shl b32 $r14 8 + sub b32 $r15 $r14 $r15 + trace_clr(T_STRINIT) + ret +') diff --git a/driver/pscnv/nvc0_graph.h b/driver/pscnv/nvc0_graph.h new file mode 100644 index 00000000..119c36c3 --- /dev/null +++ b/driver/pscnv/nvc0_graph.h @@ -0,0 +1,79 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#ifndef __NVC0_GRAPH_H__ +#define __NVC0_GRAPH_H__ + +#define NVC0_TP_MAX 32 +#define NVC0_GPC_MAX 4 + +#define NVC0_GRAPH(x) container_of(x, struct nvc0_graph_engine, base) + +struct nvc0_graph_engine { + struct pscnv_engine base; + spinlock_t lock; + uint32_t grctx_size; + uint32_t *grctx_initvals; + uint8_t ropc_count; + uint8_t gpc_count; + uint8_t tp_count; + uint8_t gpc_tp_count[NVC0_GPC_MAX]; + uint8_t gpc_cx_count[NVC0_GPC_MAX]; + struct pscnv_bo *obj188b4; + struct pscnv_bo *obj188b8; + struct pscnv_bo *obj08004; + struct pscnv_bo *obj0800c; + struct pscnv_bo *obj19848; + uint32_t magic_val; /* XXX */ +}; + +/* nvc0_graph.c uses this also to determine supported chipsets */ +static inline u32 +nvc0_graph_class(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + switch (dev_priv->chipset) { + case 0xc0: + case 0xc3: + case 0xc4: + case 0xce: /* guess, mmio trace shows only 0x9097 state */ + case 0xcf: /* guess, mmio trace shows only 0x9097 state */ + return 0x9097; + case 0xc1: + return 0x9197; + case 0xc8: + return 0x9297; + default: + return 0; + } +} + +extern int nvc0_grctx_construct(struct drm_device *dev, + struct nvc0_graph_engine *graph, + struct pscnv_chan *chan); + +#endif diff --git a/driver/pscnv/nvc0_grctx.c b/driver/pscnv/nvc0_grctx.c new file mode 100644 index 00000000..a0fdf5cf --- /dev/null +++ b/driver/pscnv/nvc0_grctx.c @@ -0,0 +1,3009 @@ + +#include "drmP.h" +#include "nouveau_drv.h" +#include "nouveau_reg.h" +#include "pscnv_chan.h" + +#include "nvc0_vm.h" +#include "nvc0_graph.h" + +#include "nvc0_pgraph.xml.h" + +#define GPC_REG(i, r) (NVC0_PGRAPH_GPC(i) + (r)) +#define TP_REG(i, j, r) (NVC0_PGRAPH_GPC_TP(i, j) + (r)) +#define UNK6000(n) NVC0_PGRAPH_UNK6000_##n +#define UNK5800(n) NVC0_PGRAPH_UNK5800_##n +#define GPC_BC(n) NVC0_PGRAPH_GPC_BROADCAST_##n + +static void nvc0_grctx_init_icmds(struct drm_device *dev); + +static void nvc0_grctx_init_dispatch(struct drm_device *dev); +static void nvc0_grctx_init_macro(struct drm_device *dev); +static void nvc0_grctx_init_m2mf(struct drm_device *dev); +static void nvc0_grctx_init_unk47xx(struct drm_device *dev); +static void nvc0_grctx_init_shaders(struct drm_device *dev); +static void nvc0_grctx_init_unk60xx(struct drm_device *dev); +static void nvc0_grctx_init_unk64xx(struct drm_device *dev); +static void nvc0_grctx_init_tpbus(struct drm_device *dev); +static void nvc0_grctx_init_ccache(struct drm_device *dev); + +static void nvc0_grctx_init_gpc(struct drm_device *dev); +static void nvc0_grctx_init_tp(struct drm_device *dev); +static void nvc0_grctx_init_ropc(struct drm_device *dev); + +static void nvc0_grctx_init_9097(struct drm_device *dev); +static void nvc0_grctx_init_9197(struct drm_device *dev); +static void nvc0_grctx_init_9297(struct drm_device *dev); +static void nvc0_grctx_init_902d(struct drm_device *dev); +static void nvc0_grctx_init_9039(struct drm_device *dev); +static void nvc0_grctx_init_90c0(struct drm_device *dev); + +int +nvc0_grctx_construct(struct drm_device *dev, + struct nvc0_graph_engine *graph, + struct pscnv_chan *chan) +{ + struct nvc0_vspace *vs = nvc0_vs(chan->vspace); + uint32_t val260; + uint32_t fermi = nvc0_graph_class(dev); + int gpc_tp_count_max = 0; + int i; + + for (i = 0; i < graph->gpc_count; ++i) { + if (gpc_tp_count_max < graph->gpc_tp_count[i]) + gpc_tp_count_max = graph->gpc_tp_count[i]; + } + + val260 = nv_rd32(dev, 0x260); + nv_wr32(dev, 0x260, val260 & ~1); + nv_wr32(dev, NVC0_PGRAPH_ICMD_DATA, 0x00000000); + nv_wr32(dev, 0x400208, 0x00000000); + + nvc0_grctx_init_dispatch(dev); + nvc0_grctx_init_macro(dev); + nvc0_grctx_init_m2mf(dev); + nvc0_grctx_init_unk47xx(dev); + nvc0_grctx_init_shaders(dev); + nvc0_grctx_init_unk60xx(dev); + nvc0_grctx_init_unk64xx(dev); + nvc0_grctx_init_tpbus(dev); + nvc0_grctx_init_ccache(dev); + nvc0_grctx_init_ropc(dev); + nvc0_grctx_init_gpc(dev); + nvc0_grctx_init_tp(dev); + + nv_wr32(dev, 0x404154, 0x00000000); + + /* fuc "mmio list" writes */ + for (i = 0; i < vs->mmio_count * 8; i += 8) { + uint32_t reg = nv_rv32(vs->mmio_bo, i + 0); + nv_wr32(dev, reg, nv_rv32(vs->mmio_bo, i + 4)); + } + + { + int gpc, tp, id; + for (tp = 0, id = 0; tp < gpc_tp_count_max; tp++) { + for (gpc = 0; gpc < graph->gpc_count; gpc++) { + if (tp < graph->gpc_tp_count[gpc]) { + nv_wr32(dev, TP_REG(gpc, tp, 0x698), id); + nv_wr32(dev, TP_REG(gpc, tp, 0x4e8), id); + nv_wr32(dev, GPC_REG(gpc, 0x0c10 + tp * 4), id); + nv_wr32(dev, TP_REG(gpc, tp, 0x088), id); + id++; + } + nv_wr32(dev, GPC_REG(gpc, 0x0c08), graph->gpc_tp_count[gpc]); + nv_wr32(dev, GPC_REG(gpc, 0x0c8c), graph->gpc_tp_count[gpc]); + } + } + } + + { + uint32_t tp_bitfield = 0; + for (i = 1; i < graph->gpc_count; i++) + tp_bitfield |= graph->gpc_tp_count[i] << (i * 4); + + nv_wr32(dev, UNK6000(GPC_TPCNT(0)), tp_bitfield); + nv_wr32(dev, UNK5800(GPC_TPCNT(0)), tp_bitfield); + + for (i = 1; i < graph->gpc_count; i++) { + nv_wr32(dev, UNK6000(GPC_TPCNT(i)), 0x00000000); + nv_wr32(dev, UNK5800(GPC_TPCNT(i)), 0x00000000); + } + } + + /* every 8-bit word shows a TP number and the presence of the TP. */ + { + uint8_t gpc_tp_count[NVC0_GPC_MAX], data[NVC0_TP_MAX]; + int gpc, tp; + + memcpy(gpc_tp_count, graph->gpc_tp_count, sizeof(graph->gpc_tp_count)); + memset(data, 0x1f, sizeof(data)); + + gpc = -1; + for (tp = 0; tp < graph->tp_count; tp++) { + do { + gpc = (gpc + 1) % graph->gpc_count; + } while (!gpc_tp_count[gpc]); + gpc_tp_count[gpc]--; + data[tp] = gpc; + } + + for (i = 0; i < gpc_tp_count_max; i++) + nv_wr32(dev, UNK6000(TP_GPCID(i)), ((uint32_t *)data)[i]); + } + + /******* TP broadcast section starts. ******/ + { + uint32_t data[6] = {}; + uint32_t data2[2] = {}; + uint8_t gpc_tp_count[NVC0_GPC_MAX]; + uint8_t shift, ntpcv; + int gpc, tp; + + /* some initial assignment of TPs at 0x418b08 + x. + Example: + GTX470 has 2 TP0's, 4 TP1's, 4 TP2's, and 4 TP3's. + GTX480 has 3 TP0's, 4 TP1's, 4 TP2's, and 4 TP3's. + in other words, TP0/TP1 in GTX470 and TP0 in GTX480 don't have TP0. + therefore we set 2,3,0,1,2,3,0,1,2,3,0,1,2,3 for GTX470, + and 1,2,3,0,1,2,3,0,1,2,3,0,1,2,3 for GTX480. + the remaining fields are filled with 7. + one mystery: the blob sets 2,3,0,1,2,3,0,1,2,3,1,2,3,0 for GTX470. + */ + memcpy(gpc_tp_count, graph->gpc_tp_count, sizeof(graph->gpc_tp_count)); + + gpc = -1; + for (tp = 0; tp < graph->tp_count; tp++) { + do { + gpc = (gpc + 1) % graph->gpc_count; + } while (!gpc_tp_count[gpc]); + gpc_tp_count[gpc]--; + + data[tp / 6] |= gpc << ((tp % 6) * 5); + } + + for (; tp < NVC0_TP_MAX; tp++) + data[tp / 6] |= 7 << ((tp % 6) * 5); + + /* the following are how to determine 419bd0 and 419be0. + let's define shift, ntpcv, and data2[] as follows. + shift is a shift amount that makes bit 4 of (tp_count << shift) + equal to 1. + ntpcv is a normalized tp_count: ntpcv = tp_count << shift. + data2[i] = (1 << (i + 5)) % ntpcv. + now, you can derive: + 419bd0: 0-7 ???, 8-15 tp_count, 16-20 ntpcv, 21-23 shift, and + 24-28 data2[0]. + 419be4: 0-4 data2[1], 5-9 data2[2], 10-14 data2[3], + 15-19 data2[4], 20-24 data2[5], and 25-29 data2[6]. */ + shift = 0; + ntpcv = graph->tp_count; + while (!(ntpcv & (1 << 4))) { + ntpcv <<= 1; + shift++; + } + + data2[0] = (ntpcv << 16); + data2[0] |= (shift << 21); + data2[0] |= (((1 << (0 + 5)) % ntpcv) << 24); + for (i = 1; i < 7; i++) + data2[1] |= ((1 << (i + 5)) % ntpcv) << ((i - 1) * 5); + + /* GPC_BROADCAST */ + nv_wr32(dev, GPC_BC(TPBUS_TOTAL), + (graph->tp_count << 8) | graph->magic_val); + for (i = 0; i < 6; i++) + nv_wr32(dev, GPC_BC(TPBUS_TP_GPCID(i)), data[i]); + + /* GPC_BROADCAST.TP_BROADCAST */ + nv_wr32(dev, GPC_BC(TP_BROADCAST_TPBUS_UNKD0), + (graph->tp_count << 8) | graph->magic_val | data2[0]); + nv_wr32(dev, GPC_BC(TP_BROADCAST_TPBUS_UNKE4), data2[1]); + for (i = 0; i < 6; i++) + nv_wr32(dev, GPC_BC(TP_BROADCAST_TPBUS_TP_GPCID(i)), data[i]); + + /* TPBUS */ + nv_wr32(dev, NVC0_PGRAPH_TPBUS_TOTAL, + (graph->tp_count << 8) | graph->magic_val); + for (i = 0; i < 6; i++) + nv_wr32(dev, NVC0_PGRAPH_TPBUS_TP_GPCID(i), data[i]); + } + + { + uint32_t tp_mask = 0, tp_set = 0; + uint8_t gpc_tp_count[NVC0_GPC_MAX]; + int gpc, tp; + + memcpy(gpc_tp_count, graph->gpc_tp_count, sizeof(graph->gpc_tp_count)); + + /* example: GTX470=0x0f0f0707 and GTX480=0x0f0f0f07. */ + for (gpc = 0; gpc < graph->gpc_count; gpc++) + tp_mask |= ((1 << graph->gpc_tp_count[gpc]) - 1) << (gpc * 8); + + gpc = -1; + for (i = 0, gpc = -1; i < 32; i++) { + int ltp = i * (graph->tp_count - 1) / 32; + + do { + gpc = (gpc + 1) % graph->gpc_count; + } while (!gpc_tp_count[gpc]); + tp = graph->gpc_tp_count[gpc] - gpc_tp_count[gpc]--; + + tp_set |= 1 << ((gpc * 8) + tp); + + do { + nv_wr32(dev, NVC0_PGRAPH_TPGRAD(0, i), tp_set); + tp_set ^= tp_mask; + nv_wr32(dev, NVC0_PGRAPH_TPGRAD(1, i), tp_set); + tp_set ^= tp_mask; + } while (ltp == (++i * (graph->tp_count - 1) / 32)); + i--; + } + } + + /* phase 2 */ + nvc0_grctx_init_icmds(dev); + + /* phase 3 */ + nv_wr32(dev, 0x404154, 0x400); + + nvc0_grctx_init_9097(dev); + if (fermi >= 0x9197) + nvc0_grctx_init_9197(dev); + if (fermi >= 0x9297) + nvc0_grctx_init_9297(dev); + nvc0_grctx_init_902d(dev); + nvc0_grctx_init_9039(dev); + nvc0_grctx_init_90c0(dev); + + nv_wr32(dev, 0x260, val260); + + return 0; +} + +static void +nv_icmd(struct drm_device *dev, uint32_t icmd, uint32_t data) +{ + nv_wr32(dev, NVC0_PGRAPH_ICMD_DATA, data); + nv_wr32(dev, NVC0_PGRAPH_ICMD_CMD, icmd); + while (nv_rd32(dev, NVC0_PGRAPH_STATUS) & 2) { } +} + +static void +nvc0_grctx_init_icmds(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + nv_wr32(dev, 0x400208, 0x80000000); + + nv_icmd(dev, 0x00001000, 0x00000004); + nv_icmd(dev, 0x000000a9, 0x0000ffff); + nv_icmd(dev, 0x00000038, 0x0fac6881); + nv_icmd(dev, 0x0000003d, 0x00000001); + nv_icmd(dev, 0x000000e8, 0x00000400); + nv_icmd(dev, 0x000000e9, 0x00000400); + nv_icmd(dev, 0x000000ea, 0x00000400); + nv_icmd(dev, 0x000000eb, 0x00000400); + nv_icmd(dev, 0x000000ec, 0x00000400); + nv_icmd(dev, 0x000000ed, 0x00000400); + nv_icmd(dev, 0x000000ee, 0x00000400); + nv_icmd(dev, 0x000000ef, 0x00000400); + nv_icmd(dev, 0x00000078, 0x00000300); + nv_icmd(dev, 0x00000079, 0x00000300); + nv_icmd(dev, 0x0000007a, 0x00000300); + nv_icmd(dev, 0x0000007b, 0x00000300); + nv_icmd(dev, 0x0000007c, 0x00000300); + nv_icmd(dev, 0x0000007d, 0x00000300); + nv_icmd(dev, 0x0000007e, 0x00000300); + nv_icmd(dev, 0x0000007f, 0x00000300); + nv_icmd(dev, 0x00000050, 0x00000011); + nv_icmd(dev, 0x00000058, 0x00000008); + nv_icmd(dev, 0x00000059, 0x00000008); + nv_icmd(dev, 0x0000005a, 0x00000008); + nv_icmd(dev, 0x0000005b, 0x00000008); + nv_icmd(dev, 0x0000005c, 0x00000008); + nv_icmd(dev, 0x0000005d, 0x00000008); + nv_icmd(dev, 0x0000005e, 0x00000008); + nv_icmd(dev, 0x0000005f, 0x00000008); + nv_icmd(dev, 0x00000208, 0x00000001); + nv_icmd(dev, 0x00000209, 0x00000001); + nv_icmd(dev, 0x0000020a, 0x00000001); + nv_icmd(dev, 0x0000020b, 0x00000001); + nv_icmd(dev, 0x0000020c, 0x00000001); + nv_icmd(dev, 0x0000020d, 0x00000001); + nv_icmd(dev, 0x0000020e, 0x00000001); + nv_icmd(dev, 0x0000020f, 0x00000001); + nv_icmd(dev, 0x00000081, 0x00000001); + nv_icmd(dev, 0x00000085, 0x00000004); + nv_icmd(dev, 0x00000088, 0x00000400); + nv_icmd(dev, 0x00000090, 0x00000300); + nv_icmd(dev, 0x00000098, 0x00001001); + nv_icmd(dev, 0x000000e3, 0x00000001); + nv_icmd(dev, 0x000000da, 0x00000001); + nv_icmd(dev, 0x000000f8, 0x00000003); + nv_icmd(dev, 0x000000fa, 0x00000001); + nv_icmd(dev, 0x0000009f, 0x0000ffff); + nv_icmd(dev, 0x000000a0, 0x0000ffff); + nv_icmd(dev, 0x000000a1, 0x0000ffff); + nv_icmd(dev, 0x000000a2, 0x0000ffff); + nv_icmd(dev, 0x000000b1, 0x00000001); + nv_icmd(dev, 0x000000b2, 0x00000000); + nv_icmd(dev, 0x000000b3, 0x00000000); + nv_icmd(dev, 0x000000b4, 0x00000000); + nv_icmd(dev, 0x000000b5, 0x00000000); + nv_icmd(dev, 0x000000b6, 0x00000000); + nv_icmd(dev, 0x000000b7, 0x00000000); + nv_icmd(dev, 0x000000b8, 0x00000000); + nv_icmd(dev, 0x000000b9, 0x00000000); + nv_icmd(dev, 0x000000ba, 0x00000000); + nv_icmd(dev, 0x000000bb, 0x00000000); + nv_icmd(dev, 0x000000bc, 0x00000000); + nv_icmd(dev, 0x000000bd, 0x00000000); + nv_icmd(dev, 0x000000be, 0x00000000); + nv_icmd(dev, 0x000000bf, 0x00000000); + nv_icmd(dev, 0x000000c0, 0x00000000); + nv_icmd(dev, 0x000000c1, 0x00000000); + nv_icmd(dev, 0x000000c2, 0x00000000); + nv_icmd(dev, 0x000000c3, 0x00000000); + nv_icmd(dev, 0x000000c4, 0x00000000); + nv_icmd(dev, 0x000000c5, 0x00000000); + nv_icmd(dev, 0x000000c6, 0x00000000); + nv_icmd(dev, 0x000000c7, 0x00000000); + nv_icmd(dev, 0x000000c8, 0x00000000); + nv_icmd(dev, 0x000000c9, 0x00000000); + nv_icmd(dev, 0x000000ca, 0x00000000); + nv_icmd(dev, 0x000000cb, 0x00000000); + nv_icmd(dev, 0x000000cc, 0x00000000); + nv_icmd(dev, 0x000000cd, 0x00000000); + nv_icmd(dev, 0x000000ce, 0x00000000); + nv_icmd(dev, 0x000000cf, 0x00000000); + nv_icmd(dev, 0x000000d0, 0x00000000); + nv_icmd(dev, 0x000000d1, 0x00000000); + nv_icmd(dev, 0x000000d2, 0x00000000); + nv_icmd(dev, 0x000000d3, 0x00000000); + nv_icmd(dev, 0x000000d4, 0x00000000); + nv_icmd(dev, 0x000000d5, 0x00000000); + nv_icmd(dev, 0x000000d6, 0x00000000); + nv_icmd(dev, 0x000000d7, 0x00000000); + nv_icmd(dev, 0x000000d8, 0x00000000); + nv_icmd(dev, 0x000000d9, 0x00000000); + nv_icmd(dev, 0x00000210, 0x00000040); + nv_icmd(dev, 0x00000211, 0x00000040); + nv_icmd(dev, 0x00000212, 0x00000040); + nv_icmd(dev, 0x00000213, 0x00000040); + nv_icmd(dev, 0x00000214, 0x00000040); + nv_icmd(dev, 0x00000215, 0x00000040); + nv_icmd(dev, 0x00000216, 0x00000040); + nv_icmd(dev, 0x00000217, 0x00000040); + nv_icmd(dev, 0x00000218, 0x0000c080); + nv_icmd(dev, 0x00000219, 0x0000c080); + nv_icmd(dev, 0x0000021a, 0x0000c080); + nv_icmd(dev, 0x0000021b, 0x0000c080); + nv_icmd(dev, 0x0000021c, 0x0000c080); + nv_icmd(dev, 0x0000021d, 0x0000c080); + nv_icmd(dev, 0x0000021e, 0x0000c080); + nv_icmd(dev, 0x0000021f, 0x0000c080); + nv_icmd(dev, 0x000000ad, 0x0000013e); + nv_icmd(dev, 0x000000e1, 0x00000010); + nv_icmd(dev, 0x00000290, 0x00000000); + nv_icmd(dev, 0x00000291, 0x00000000); + nv_icmd(dev, 0x00000292, 0x00000000); + nv_icmd(dev, 0x00000293, 0x00000000); + nv_icmd(dev, 0x00000294, 0x00000000); + nv_icmd(dev, 0x00000295, 0x00000000); + nv_icmd(dev, 0x00000296, 0x00000000); + nv_icmd(dev, 0x00000297, 0x00000000); + nv_icmd(dev, 0x00000298, 0x00000000); + nv_icmd(dev, 0x00000299, 0x00000000); + nv_icmd(dev, 0x0000029a, 0x00000000); + nv_icmd(dev, 0x0000029b, 0x00000000); + nv_icmd(dev, 0x0000029c, 0x00000000); + nv_icmd(dev, 0x0000029d, 0x00000000); + nv_icmd(dev, 0x0000029e, 0x00000000); + nv_icmd(dev, 0x0000029f, 0x00000000); + nv_icmd(dev, 0x000003b0, 0x00000000); + nv_icmd(dev, 0x000003b1, 0x00000000); + nv_icmd(dev, 0x000003b2, 0x00000000); + nv_icmd(dev, 0x000003b3, 0x00000000); + nv_icmd(dev, 0x000003b4, 0x00000000); + nv_icmd(dev, 0x000003b5, 0x00000000); + nv_icmd(dev, 0x000003b6, 0x00000000); + nv_icmd(dev, 0x000003b7, 0x00000000); + nv_icmd(dev, 0x000003b8, 0x00000000); + nv_icmd(dev, 0x000003b9, 0x00000000); + nv_icmd(dev, 0x000003ba, 0x00000000); + nv_icmd(dev, 0x000003bb, 0x00000000); + nv_icmd(dev, 0x000003bc, 0x00000000); + nv_icmd(dev, 0x000003bd, 0x00000000); + nv_icmd(dev, 0x000003be, 0x00000000); + nv_icmd(dev, 0x000003bf, 0x00000000); + nv_icmd(dev, 0x000002a0, 0x00000000); + nv_icmd(dev, 0x000002a1, 0x00000000); + nv_icmd(dev, 0x000002a2, 0x00000000); + nv_icmd(dev, 0x000002a3, 0x00000000); + nv_icmd(dev, 0x000002a4, 0x00000000); + nv_icmd(dev, 0x000002a5, 0x00000000); + nv_icmd(dev, 0x000002a6, 0x00000000); + nv_icmd(dev, 0x000002a7, 0x00000000); + nv_icmd(dev, 0x000002a8, 0x00000000); + nv_icmd(dev, 0x000002a9, 0x00000000); + nv_icmd(dev, 0x000002aa, 0x00000000); + nv_icmd(dev, 0x000002ab, 0x00000000); + nv_icmd(dev, 0x000002ac, 0x00000000); + nv_icmd(dev, 0x000002ad, 0x00000000); + nv_icmd(dev, 0x000002ae, 0x00000000); + nv_icmd(dev, 0x000002af, 0x00000000); + nv_icmd(dev, 0x00000420, 0x00000000); + nv_icmd(dev, 0x00000421, 0x00000000); + nv_icmd(dev, 0x00000422, 0x00000000); + nv_icmd(dev, 0x00000423, 0x00000000); + nv_icmd(dev, 0x00000424, 0x00000000); + nv_icmd(dev, 0x00000425, 0x00000000); + nv_icmd(dev, 0x00000426, 0x00000000); + nv_icmd(dev, 0x00000427, 0x00000000); + nv_icmd(dev, 0x00000428, 0x00000000); + nv_icmd(dev, 0x00000429, 0x00000000); + nv_icmd(dev, 0x0000042a, 0x00000000); + nv_icmd(dev, 0x0000042b, 0x00000000); + nv_icmd(dev, 0x0000042c, 0x00000000); + nv_icmd(dev, 0x0000042d, 0x00000000); + nv_icmd(dev, 0x0000042e, 0x00000000); + nv_icmd(dev, 0x0000042f, 0x00000000); + nv_icmd(dev, 0x000002b0, 0x00000000); + nv_icmd(dev, 0x000002b1, 0x00000000); + nv_icmd(dev, 0x000002b2, 0x00000000); + nv_icmd(dev, 0x000002b3, 0x00000000); + nv_icmd(dev, 0x000002b4, 0x00000000); + nv_icmd(dev, 0x000002b5, 0x00000000); + nv_icmd(dev, 0x000002b6, 0x00000000); + nv_icmd(dev, 0x000002b7, 0x00000000); + nv_icmd(dev, 0x000002b8, 0x00000000); + nv_icmd(dev, 0x000002b9, 0x00000000); + nv_icmd(dev, 0x000002ba, 0x00000000); + nv_icmd(dev, 0x000002bb, 0x00000000); + nv_icmd(dev, 0x000002bc, 0x00000000); + nv_icmd(dev, 0x000002bd, 0x00000000); + nv_icmd(dev, 0x000002be, 0x00000000); + nv_icmd(dev, 0x000002bf, 0x00000000); + nv_icmd(dev, 0x00000430, 0x00000000); + nv_icmd(dev, 0x00000431, 0x00000000); + nv_icmd(dev, 0x00000432, 0x00000000); + nv_icmd(dev, 0x00000433, 0x00000000); + nv_icmd(dev, 0x00000434, 0x00000000); + nv_icmd(dev, 0x00000435, 0x00000000); + nv_icmd(dev, 0x00000436, 0x00000000); + nv_icmd(dev, 0x00000437, 0x00000000); + nv_icmd(dev, 0x00000438, 0x00000000); + nv_icmd(dev, 0x00000439, 0x00000000); + nv_icmd(dev, 0x0000043a, 0x00000000); + nv_icmd(dev, 0x0000043b, 0x00000000); + nv_icmd(dev, 0x0000043c, 0x00000000); + nv_icmd(dev, 0x0000043d, 0x00000000); + nv_icmd(dev, 0x0000043e, 0x00000000); + nv_icmd(dev, 0x0000043f, 0x00000000); + nv_icmd(dev, 0x000002c0, 0x00000000); + nv_icmd(dev, 0x000002c1, 0x00000000); + nv_icmd(dev, 0x000002c2, 0x00000000); + nv_icmd(dev, 0x000002c3, 0x00000000); + nv_icmd(dev, 0x000002c4, 0x00000000); + nv_icmd(dev, 0x000002c5, 0x00000000); + nv_icmd(dev, 0x000002c6, 0x00000000); + nv_icmd(dev, 0x000002c7, 0x00000000); + nv_icmd(dev, 0x000002c8, 0x00000000); + nv_icmd(dev, 0x000002c9, 0x00000000); + nv_icmd(dev, 0x000002ca, 0x00000000); + nv_icmd(dev, 0x000002cb, 0x00000000); + nv_icmd(dev, 0x000002cc, 0x00000000); + nv_icmd(dev, 0x000002cd, 0x00000000); + nv_icmd(dev, 0x000002ce, 0x00000000); + nv_icmd(dev, 0x000002cf, 0x00000000); + nv_icmd(dev, 0x000004d0, 0x00000000); + nv_icmd(dev, 0x000004d1, 0x00000000); + nv_icmd(dev, 0x000004d2, 0x00000000); + nv_icmd(dev, 0x000004d3, 0x00000000); + nv_icmd(dev, 0x000004d4, 0x00000000); + nv_icmd(dev, 0x000004d5, 0x00000000); + nv_icmd(dev, 0x000004d6, 0x00000000); + nv_icmd(dev, 0x000004d7, 0x00000000); + nv_icmd(dev, 0x000004d8, 0x00000000); + nv_icmd(dev, 0x000004d9, 0x00000000); + nv_icmd(dev, 0x000004da, 0x00000000); + nv_icmd(dev, 0x000004db, 0x00000000); + nv_icmd(dev, 0x000004dc, 0x00000000); + nv_icmd(dev, 0x000004dd, 0x00000000); + nv_icmd(dev, 0x000004de, 0x00000000); + nv_icmd(dev, 0x000004df, 0x00000000); + nv_icmd(dev, 0x00000720, 0x00000000); + nv_icmd(dev, 0x00000721, 0x00000000); + nv_icmd(dev, 0x00000722, 0x00000000); + nv_icmd(dev, 0x00000723, 0x00000000); + nv_icmd(dev, 0x00000724, 0x00000000); + nv_icmd(dev, 0x00000725, 0x00000000); + nv_icmd(dev, 0x00000726, 0x00000000); + nv_icmd(dev, 0x00000727, 0x00000000); + nv_icmd(dev, 0x00000728, 0x00000000); + nv_icmd(dev, 0x00000729, 0x00000000); + nv_icmd(dev, 0x0000072a, 0x00000000); + nv_icmd(dev, 0x0000072b, 0x00000000); + nv_icmd(dev, 0x0000072c, 0x00000000); + nv_icmd(dev, 0x0000072d, 0x00000000); + nv_icmd(dev, 0x0000072e, 0x00000000); + nv_icmd(dev, 0x0000072f, 0x00000000); + nv_icmd(dev, 0x000008c0, 0x00000000); + nv_icmd(dev, 0x000008c1, 0x00000000); + nv_icmd(dev, 0x000008c2, 0x00000000); + nv_icmd(dev, 0x000008c3, 0x00000000); + nv_icmd(dev, 0x000008c4, 0x00000000); + nv_icmd(dev, 0x000008c5, 0x00000000); + nv_icmd(dev, 0x000008c6, 0x00000000); + nv_icmd(dev, 0x000008c7, 0x00000000); + nv_icmd(dev, 0x000008c8, 0x00000000); + nv_icmd(dev, 0x000008c9, 0x00000000); + nv_icmd(dev, 0x000008ca, 0x00000000); + nv_icmd(dev, 0x000008cb, 0x00000000); + nv_icmd(dev, 0x000008cc, 0x00000000); + nv_icmd(dev, 0x000008cd, 0x00000000); + nv_icmd(dev, 0x000008ce, 0x00000000); + nv_icmd(dev, 0x000008cf, 0x00000000); + nv_icmd(dev, 0x00000890, 0x00000000); + nv_icmd(dev, 0x00000891, 0x00000000); + nv_icmd(dev, 0x00000892, 0x00000000); + nv_icmd(dev, 0x00000893, 0x00000000); + nv_icmd(dev, 0x00000894, 0x00000000); + nv_icmd(dev, 0x00000895, 0x00000000); + nv_icmd(dev, 0x00000896, 0x00000000); + nv_icmd(dev, 0x00000897, 0x00000000); + nv_icmd(dev, 0x00000898, 0x00000000); + nv_icmd(dev, 0x00000899, 0x00000000); + nv_icmd(dev, 0x0000089a, 0x00000000); + nv_icmd(dev, 0x0000089b, 0x00000000); + nv_icmd(dev, 0x0000089c, 0x00000000); + nv_icmd(dev, 0x0000089d, 0x00000000); + nv_icmd(dev, 0x0000089e, 0x00000000); + nv_icmd(dev, 0x0000089f, 0x00000000); + nv_icmd(dev, 0x000008e0, 0x00000000); + nv_icmd(dev, 0x000008e1, 0x00000000); + nv_icmd(dev, 0x000008e2, 0x00000000); + nv_icmd(dev, 0x000008e3, 0x00000000); + nv_icmd(dev, 0x000008e4, 0x00000000); + nv_icmd(dev, 0x000008e5, 0x00000000); + nv_icmd(dev, 0x000008e6, 0x00000000); + nv_icmd(dev, 0x000008e7, 0x00000000); + nv_icmd(dev, 0x000008e8, 0x00000000); + nv_icmd(dev, 0x000008e9, 0x00000000); + nv_icmd(dev, 0x000008ea, 0x00000000); + nv_icmd(dev, 0x000008eb, 0x00000000); + nv_icmd(dev, 0x000008ec, 0x00000000); + nv_icmd(dev, 0x000008ed, 0x00000000); + nv_icmd(dev, 0x000008ee, 0x00000000); + nv_icmd(dev, 0x000008ef, 0x00000000); + nv_icmd(dev, 0x000008a0, 0x00000000); + nv_icmd(dev, 0x000008a1, 0x00000000); + nv_icmd(dev, 0x000008a2, 0x00000000); + nv_icmd(dev, 0x000008a3, 0x00000000); + nv_icmd(dev, 0x000008a4, 0x00000000); + nv_icmd(dev, 0x000008a5, 0x00000000); + nv_icmd(dev, 0x000008a6, 0x00000000); + nv_icmd(dev, 0x000008a7, 0x00000000); + nv_icmd(dev, 0x000008a8, 0x00000000); + nv_icmd(dev, 0x000008a9, 0x00000000); + nv_icmd(dev, 0x000008aa, 0x00000000); + nv_icmd(dev, 0x000008ab, 0x00000000); + nv_icmd(dev, 0x000008ac, 0x00000000); + nv_icmd(dev, 0x000008ad, 0x00000000); + nv_icmd(dev, 0x000008ae, 0x00000000); + nv_icmd(dev, 0x000008af, 0x00000000); + nv_icmd(dev, 0x000008f0, 0x00000000); + nv_icmd(dev, 0x000008f1, 0x00000000); + nv_icmd(dev, 0x000008f2, 0x00000000); + nv_icmd(dev, 0x000008f3, 0x00000000); + nv_icmd(dev, 0x000008f4, 0x00000000); + nv_icmd(dev, 0x000008f5, 0x00000000); + nv_icmd(dev, 0x000008f6, 0x00000000); + nv_icmd(dev, 0x000008f7, 0x00000000); + nv_icmd(dev, 0x000008f8, 0x00000000); + nv_icmd(dev, 0x000008f9, 0x00000000); + nv_icmd(dev, 0x000008fa, 0x00000000); + nv_icmd(dev, 0x000008fb, 0x00000000); + nv_icmd(dev, 0x000008fc, 0x00000000); + nv_icmd(dev, 0x000008fd, 0x00000000); + nv_icmd(dev, 0x000008fe, 0x00000000); + nv_icmd(dev, 0x000008ff, 0x00000000); + nv_icmd(dev, 0x0000094c, 0x000000ff); + nv_icmd(dev, 0x0000094d, 0xffffffff); + nv_icmd(dev, 0x0000094e, 0x00000002); + nv_icmd(dev, 0x000002ec, 0x00000001); + nv_icmd(dev, 0x00000303, 0x00000001); + nv_icmd(dev, 0x000002e6, 0x00000001); + nv_icmd(dev, 0x00000466, 0x00000052); + nv_icmd(dev, 0x00000301, 0x3f800000); + nv_icmd(dev, 0x00000304, 0x30201000); + nv_icmd(dev, 0x00000305, 0x70605040); + nv_icmd(dev, 0x00000306, 0xb8a89888); + nv_icmd(dev, 0x00000307, 0xf8e8d8c8); + nv_icmd(dev, 0x0000030a, 0x00ffff00); + nv_icmd(dev, 0x0000030b, 0x0000001a); + nv_icmd(dev, 0x0000030c, 0x00000001); + nv_icmd(dev, 0x00000318, 0x00000001); + nv_icmd(dev, 0x00000340, 0x00000000); + nv_icmd(dev, 0x00000375, 0x00000001); + nv_icmd(dev, 0x00000351, 0x00000100); + nv_icmd(dev, 0x0000037d, 0x00000006); + nv_icmd(dev, 0x000003a0, 0x00000002); + nv_icmd(dev, 0x000003aa, 0x00000001); + nv_icmd(dev, 0x000003a9, 0x00000001); + nv_icmd(dev, 0x00000380, 0x00000001); + nv_icmd(dev, 0x00000360, 0x00000040); + nv_icmd(dev, 0x00000366, 0x00000000); + nv_icmd(dev, 0x00000367, 0x00000000); + nv_icmd(dev, 0x00000368, 0x00001fff); + nv_icmd(dev, 0x00000370, 0x00000000); + nv_icmd(dev, 0x00000371, 0x00000000); + nv_icmd(dev, 0x00000372, 0x003fffff); + nv_icmd(dev, 0x0000037a, 0x00000012); + nv_icmd(dev, 0x000005e0, 0x00000022); + nv_icmd(dev, 0x000005e1, 0x00000022); + nv_icmd(dev, 0x000005e2, 0x00000022); + nv_icmd(dev, 0x000005e3, 0x00000022); + nv_icmd(dev, 0x000005e4, 0x00000022); + nv_icmd(dev, 0x00000619, 0x00000003); + nv_icmd(dev, 0x00000811, 0x00000003); + nv_icmd(dev, 0x00000812, 0x00000004); + nv_icmd(dev, 0x00000813, 0x00000006); + nv_icmd(dev, 0x00000814, 0x00000008); + nv_icmd(dev, 0x00000815, 0x0000000b); + nv_icmd(dev, 0x00000800, 0x00000001); + nv_icmd(dev, 0x00000801, 0x00000001); + nv_icmd(dev, 0x00000802, 0x00000001); + nv_icmd(dev, 0x00000803, 0x00000001); + nv_icmd(dev, 0x00000804, 0x00000001); + nv_icmd(dev, 0x00000805, 0x00000001); + nv_icmd(dev, 0x00000632, 0x00000001); + nv_icmd(dev, 0x00000633, 0x00000002); + nv_icmd(dev, 0x00000634, 0x00000003); + nv_icmd(dev, 0x00000635, 0x00000004); + nv_icmd(dev, 0x00000654, 0x3f800000); + nv_icmd(dev, 0x00000657, 0x3f800000); + nv_icmd(dev, 0x00000655, 0x3f800000); + nv_icmd(dev, 0x00000656, 0x3f800000); + nv_icmd(dev, 0x000006cd, 0x3f800000); + nv_icmd(dev, 0x000007f5, 0x3f800000); + nv_icmd(dev, 0x000007dc, 0x39291909); + nv_icmd(dev, 0x000007dd, 0x79695949); + nv_icmd(dev, 0x000007de, 0xb9a99989); + nv_icmd(dev, 0x000007df, 0xf9e9d9c9); + nv_icmd(dev, 0x000007e8, 0x00003210); + nv_icmd(dev, 0x000007e9, 0x00007654); + nv_icmd(dev, 0x000007ea, 0x00000098); + nv_icmd(dev, 0x000007ec, 0x39291909); + nv_icmd(dev, 0x000007ed, 0x79695949); + nv_icmd(dev, 0x000007ee, 0xb9a99989); + nv_icmd(dev, 0x000007ef, 0xf9e9d9c9); + nv_icmd(dev, 0x000007f0, 0x00003210); + nv_icmd(dev, 0x000007f1, 0x00007654); + nv_icmd(dev, 0x000007f2, 0x00000098); + nv_icmd(dev, 0x000005a5, 0x00000001); + nv_icmd(dev, 0x00000980, 0x00000000); + nv_icmd(dev, 0x00000981, 0x00000000); + nv_icmd(dev, 0x00000982, 0x00000000); + nv_icmd(dev, 0x00000983, 0x00000000); + nv_icmd(dev, 0x00000984, 0x00000000); + nv_icmd(dev, 0x00000985, 0x00000000); + nv_icmd(dev, 0x00000986, 0x00000000); + nv_icmd(dev, 0x00000987, 0x00000000); + nv_icmd(dev, 0x00000988, 0x00000000); + nv_icmd(dev, 0x00000989, 0x00000000); + nv_icmd(dev, 0x0000098a, 0x00000000); + nv_icmd(dev, 0x0000098b, 0x00000000); + nv_icmd(dev, 0x0000098c, 0x00000000); + nv_icmd(dev, 0x0000098d, 0x00000000); + nv_icmd(dev, 0x0000098e, 0x00000000); + nv_icmd(dev, 0x0000098f, 0x00000000); + nv_icmd(dev, 0x00000990, 0x00000000); + nv_icmd(dev, 0x00000991, 0x00000000); + nv_icmd(dev, 0x00000992, 0x00000000); + nv_icmd(dev, 0x00000993, 0x00000000); + nv_icmd(dev, 0x00000994, 0x00000000); + nv_icmd(dev, 0x00000995, 0x00000000); + nv_icmd(dev, 0x00000996, 0x00000000); + nv_icmd(dev, 0x00000997, 0x00000000); + nv_icmd(dev, 0x00000998, 0x00000000); + nv_icmd(dev, 0x00000999, 0x00000000); + nv_icmd(dev, 0x0000099a, 0x00000000); + nv_icmd(dev, 0x0000099b, 0x00000000); + nv_icmd(dev, 0x0000099c, 0x00000000); + nv_icmd(dev, 0x0000099d, 0x00000000); + nv_icmd(dev, 0x0000099e, 0x00000000); + nv_icmd(dev, 0x0000099f, 0x00000000); + nv_icmd(dev, 0x000009a0, 0x00000000); + nv_icmd(dev, 0x000009a1, 0x00000000); + nv_icmd(dev, 0x000009a2, 0x00000000); + nv_icmd(dev, 0x000009a3, 0x00000000); + nv_icmd(dev, 0x000009a4, 0x00000000); + nv_icmd(dev, 0x000009a5, 0x00000000); + nv_icmd(dev, 0x000009a6, 0x00000000); + nv_icmd(dev, 0x000009a7, 0x00000000); + nv_icmd(dev, 0x000009a8, 0x00000000); + nv_icmd(dev, 0x000009a9, 0x00000000); + nv_icmd(dev, 0x000009aa, 0x00000000); + nv_icmd(dev, 0x000009ab, 0x00000000); + nv_icmd(dev, 0x000009ac, 0x00000000); + nv_icmd(dev, 0x000009ad, 0x00000000); + nv_icmd(dev, 0x000009ae, 0x00000000); + nv_icmd(dev, 0x000009af, 0x00000000); + nv_icmd(dev, 0x000009b0, 0x00000000); + nv_icmd(dev, 0x000009b1, 0x00000000); + nv_icmd(dev, 0x000009b2, 0x00000000); + nv_icmd(dev, 0x000009b3, 0x00000000); + nv_icmd(dev, 0x000009b4, 0x00000000); + nv_icmd(dev, 0x000009b5, 0x00000000); + nv_icmd(dev, 0x000009b6, 0x00000000); + nv_icmd(dev, 0x000009b7, 0x00000000); + nv_icmd(dev, 0x000009b8, 0x00000000); + nv_icmd(dev, 0x000009b9, 0x00000000); + nv_icmd(dev, 0x000009ba, 0x00000000); + nv_icmd(dev, 0x000009bb, 0x00000000); + nv_icmd(dev, 0x000009bc, 0x00000000); + nv_icmd(dev, 0x000009bd, 0x00000000); + nv_icmd(dev, 0x000009be, 0x00000000); + nv_icmd(dev, 0x000009bf, 0x00000000); + nv_icmd(dev, 0x000009c0, 0x00000000); + nv_icmd(dev, 0x000009c1, 0x00000000); + nv_icmd(dev, 0x000009c2, 0x00000000); + nv_icmd(dev, 0x000009c3, 0x00000000); + nv_icmd(dev, 0x000009c4, 0x00000000); + nv_icmd(dev, 0x000009c5, 0x00000000); + nv_icmd(dev, 0x000009c6, 0x00000000); + nv_icmd(dev, 0x000009c7, 0x00000000); + nv_icmd(dev, 0x000009c8, 0x00000000); + nv_icmd(dev, 0x000009c9, 0x00000000); + nv_icmd(dev, 0x000009ca, 0x00000000); + nv_icmd(dev, 0x000009cb, 0x00000000); + nv_icmd(dev, 0x000009cc, 0x00000000); + nv_icmd(dev, 0x000009cd, 0x00000000); + nv_icmd(dev, 0x000009ce, 0x00000000); + nv_icmd(dev, 0x000009cf, 0x00000000); + nv_icmd(dev, 0x000009d0, 0x00000000); + nv_icmd(dev, 0x000009d1, 0x00000000); + nv_icmd(dev, 0x000009d2, 0x00000000); + nv_icmd(dev, 0x000009d3, 0x00000000); + nv_icmd(dev, 0x000009d4, 0x00000000); + nv_icmd(dev, 0x000009d5, 0x00000000); + nv_icmd(dev, 0x000009d6, 0x00000000); + nv_icmd(dev, 0x000009d7, 0x00000000); + nv_icmd(dev, 0x000009d8, 0x00000000); + nv_icmd(dev, 0x000009d9, 0x00000000); + nv_icmd(dev, 0x000009da, 0x00000000); + nv_icmd(dev, 0x000009db, 0x00000000); + nv_icmd(dev, 0x000009dc, 0x00000000); + nv_icmd(dev, 0x000009dd, 0x00000000); + nv_icmd(dev, 0x000009de, 0x00000000); + nv_icmd(dev, 0x000009df, 0x00000000); + nv_icmd(dev, 0x000009e0, 0x00000000); + nv_icmd(dev, 0x000009e1, 0x00000000); + nv_icmd(dev, 0x000009e2, 0x00000000); + nv_icmd(dev, 0x000009e3, 0x00000000); + nv_icmd(dev, 0x000009e4, 0x00000000); + nv_icmd(dev, 0x000009e5, 0x00000000); + nv_icmd(dev, 0x000009e6, 0x00000000); + nv_icmd(dev, 0x000009e7, 0x00000000); + nv_icmd(dev, 0x000009e8, 0x00000000); + nv_icmd(dev, 0x000009e9, 0x00000000); + nv_icmd(dev, 0x000009ea, 0x00000000); + nv_icmd(dev, 0x000009eb, 0x00000000); + nv_icmd(dev, 0x000009ec, 0x00000000); + nv_icmd(dev, 0x000009ed, 0x00000000); + nv_icmd(dev, 0x000009ee, 0x00000000); + nv_icmd(dev, 0x000009ef, 0x00000000); + nv_icmd(dev, 0x000009f0, 0x00000000); + nv_icmd(dev, 0x000009f1, 0x00000000); + nv_icmd(dev, 0x000009f2, 0x00000000); + nv_icmd(dev, 0x000009f3, 0x00000000); + nv_icmd(dev, 0x000009f4, 0x00000000); + nv_icmd(dev, 0x000009f5, 0x00000000); + nv_icmd(dev, 0x000009f6, 0x00000000); + nv_icmd(dev, 0x000009f7, 0x00000000); + nv_icmd(dev, 0x000009f8, 0x00000000); + nv_icmd(dev, 0x000009f9, 0x00000000); + nv_icmd(dev, 0x000009fa, 0x00000000); + nv_icmd(dev, 0x000009fb, 0x00000000); + nv_icmd(dev, 0x000009fc, 0x00000000); + nv_icmd(dev, 0x000009fd, 0x00000000); + nv_icmd(dev, 0x000009fe, 0x00000000); + nv_icmd(dev, 0x000009ff, 0x00000000); + nv_icmd(dev, 0x00000468, 0x00000004); + nv_icmd(dev, 0x0000046c, 0x00000001); + nv_icmd(dev, 0x00000470, 0x00000000); + nv_icmd(dev, 0x00000471, 0x00000000); + nv_icmd(dev, 0x00000472, 0x00000000); + nv_icmd(dev, 0x00000473, 0x00000000); + nv_icmd(dev, 0x00000474, 0x00000000); + nv_icmd(dev, 0x00000475, 0x00000000); + nv_icmd(dev, 0x00000476, 0x00000000); + nv_icmd(dev, 0x00000477, 0x00000000); + nv_icmd(dev, 0x00000478, 0x00000000); + nv_icmd(dev, 0x00000479, 0x00000000); + nv_icmd(dev, 0x0000047a, 0x00000000); + nv_icmd(dev, 0x0000047b, 0x00000000); + nv_icmd(dev, 0x0000047c, 0x00000000); + nv_icmd(dev, 0x0000047d, 0x00000000); + nv_icmd(dev, 0x0000047e, 0x00000000); + nv_icmd(dev, 0x0000047f, 0x00000000); + nv_icmd(dev, 0x00000480, 0x00000000); + nv_icmd(dev, 0x00000481, 0x00000000); + nv_icmd(dev, 0x00000482, 0x00000000); + nv_icmd(dev, 0x00000483, 0x00000000); + nv_icmd(dev, 0x00000484, 0x00000000); + nv_icmd(dev, 0x00000485, 0x00000000); + nv_icmd(dev, 0x00000486, 0x00000000); + nv_icmd(dev, 0x00000487, 0x00000000); + nv_icmd(dev, 0x00000488, 0x00000000); + nv_icmd(dev, 0x00000489, 0x00000000); + nv_icmd(dev, 0x0000048a, 0x00000000); + nv_icmd(dev, 0x0000048b, 0x00000000); + nv_icmd(dev, 0x0000048c, 0x00000000); + nv_icmd(dev, 0x0000048d, 0x00000000); + nv_icmd(dev, 0x0000048e, 0x00000000); + nv_icmd(dev, 0x0000048f, 0x00000000); + nv_icmd(dev, 0x00000490, 0x00000000); + nv_icmd(dev, 0x00000491, 0x00000000); + nv_icmd(dev, 0x00000492, 0x00000000); + nv_icmd(dev, 0x00000493, 0x00000000); + nv_icmd(dev, 0x00000494, 0x00000000); + nv_icmd(dev, 0x00000495, 0x00000000); + nv_icmd(dev, 0x00000496, 0x00000000); + nv_icmd(dev, 0x00000497, 0x00000000); + nv_icmd(dev, 0x00000498, 0x00000000); + nv_icmd(dev, 0x00000499, 0x00000000); + nv_icmd(dev, 0x0000049a, 0x00000000); + nv_icmd(dev, 0x0000049b, 0x00000000); + nv_icmd(dev, 0x0000049c, 0x00000000); + nv_icmd(dev, 0x0000049d, 0x00000000); + nv_icmd(dev, 0x0000049e, 0x00000000); + nv_icmd(dev, 0x0000049f, 0x00000000); + nv_icmd(dev, 0x000004a0, 0x00000000); + nv_icmd(dev, 0x000004a1, 0x00000000); + nv_icmd(dev, 0x000004a2, 0x00000000); + nv_icmd(dev, 0x000004a3, 0x00000000); + nv_icmd(dev, 0x000004a4, 0x00000000); + nv_icmd(dev, 0x000004a5, 0x00000000); + nv_icmd(dev, 0x000004a6, 0x00000000); + nv_icmd(dev, 0x000004a7, 0x00000000); + nv_icmd(dev, 0x000004a8, 0x00000000); + nv_icmd(dev, 0x000004a9, 0x00000000); + nv_icmd(dev, 0x000004aa, 0x00000000); + nv_icmd(dev, 0x000004ab, 0x00000000); + nv_icmd(dev, 0x000004ac, 0x00000000); + nv_icmd(dev, 0x000004ad, 0x00000000); + nv_icmd(dev, 0x000004ae, 0x00000000); + nv_icmd(dev, 0x000004af, 0x00000000); + nv_icmd(dev, 0x000004b0, 0x00000000); + nv_icmd(dev, 0x000004b1, 0x00000000); + nv_icmd(dev, 0x000004b2, 0x00000000); + nv_icmd(dev, 0x000004b3, 0x00000000); + nv_icmd(dev, 0x000004b4, 0x00000000); + nv_icmd(dev, 0x000004b5, 0x00000000); + nv_icmd(dev, 0x000004b6, 0x00000000); + nv_icmd(dev, 0x000004b7, 0x00000000); + nv_icmd(dev, 0x000004b8, 0x00000000); + nv_icmd(dev, 0x000004b9, 0x00000000); + nv_icmd(dev, 0x000004ba, 0x00000000); + nv_icmd(dev, 0x000004bb, 0x00000000); + nv_icmd(dev, 0x000004bc, 0x00000000); + nv_icmd(dev, 0x000004bd, 0x00000000); + nv_icmd(dev, 0x000004be, 0x00000000); + nv_icmd(dev, 0x000004bf, 0x00000000); + nv_icmd(dev, 0x000004c0, 0x00000000); + nv_icmd(dev, 0x000004c1, 0x00000000); + nv_icmd(dev, 0x000004c2, 0x00000000); + nv_icmd(dev, 0x000004c3, 0x00000000); + nv_icmd(dev, 0x000004c4, 0x00000000); + nv_icmd(dev, 0x000004c5, 0x00000000); + nv_icmd(dev, 0x000004c6, 0x00000000); + nv_icmd(dev, 0x000004c7, 0x00000000); + nv_icmd(dev, 0x000004c8, 0x00000000); + nv_icmd(dev, 0x000004c9, 0x00000000); + nv_icmd(dev, 0x000004ca, 0x00000000); + nv_icmd(dev, 0x000004cb, 0x00000000); + nv_icmd(dev, 0x000004cc, 0x00000000); + nv_icmd(dev, 0x000004cd, 0x00000000); + nv_icmd(dev, 0x000004ce, 0x00000000); + nv_icmd(dev, 0x000004cf, 0x00000000); + nv_icmd(dev, 0x00000510, 0x3f800000); + nv_icmd(dev, 0x00000511, 0x3f800000); + nv_icmd(dev, 0x00000512, 0x3f800000); + nv_icmd(dev, 0x00000513, 0x3f800000); + nv_icmd(dev, 0x00000514, 0x3f800000); + nv_icmd(dev, 0x00000515, 0x3f800000); + nv_icmd(dev, 0x00000516, 0x3f800000); + nv_icmd(dev, 0x00000517, 0x3f800000); + nv_icmd(dev, 0x00000518, 0x3f800000); + nv_icmd(dev, 0x00000519, 0x3f800000); + nv_icmd(dev, 0x0000051a, 0x3f800000); + nv_icmd(dev, 0x0000051b, 0x3f800000); + nv_icmd(dev, 0x0000051c, 0x3f800000); + nv_icmd(dev, 0x0000051d, 0x3f800000); + nv_icmd(dev, 0x0000051e, 0x3f800000); + nv_icmd(dev, 0x0000051f, 0x3f800000); + nv_icmd(dev, 0x00000520, 0x000002b6); + nv_icmd(dev, 0x00000529, 0x00000001); + nv_icmd(dev, 0x00000530, 0xffff0000); + nv_icmd(dev, 0x00000531, 0xffff0000); + nv_icmd(dev, 0x00000532, 0xffff0000); + nv_icmd(dev, 0x00000533, 0xffff0000); + nv_icmd(dev, 0x00000534, 0xffff0000); + nv_icmd(dev, 0x00000535, 0xffff0000); + nv_icmd(dev, 0x00000536, 0xffff0000); + nv_icmd(dev, 0x00000537, 0xffff0000); + nv_icmd(dev, 0x00000538, 0xffff0000); + nv_icmd(dev, 0x00000539, 0xffff0000); + nv_icmd(dev, 0x0000053a, 0xffff0000); + nv_icmd(dev, 0x0000053b, 0xffff0000); + nv_icmd(dev, 0x0000053c, 0xffff0000); + nv_icmd(dev, 0x0000053d, 0xffff0000); + nv_icmd(dev, 0x0000053e, 0xffff0000); + nv_icmd(dev, 0x0000053f, 0xffff0000); + nv_icmd(dev, 0x00000585, 0x0000003f); + nv_icmd(dev, 0x00000576, 0x00000003); + if (dev_priv->chipset == 0xc1) + nv_icmd(dev, 0x0000057b, 0x00000059); + nv_icmd(dev, 0x00000586, 0x00000040); + nv_icmd(dev, 0x00000582, 0x00000080); + nv_icmd(dev, 0x00000583, 0x00000080); + nv_icmd(dev, 0x000005c2, 0x00000001); + nv_icmd(dev, 0x00000638, 0x00000001); + nv_icmd(dev, 0x00000639, 0x00000001); + nv_icmd(dev, 0x0000063a, 0x00000002); + nv_icmd(dev, 0x0000063b, 0x00000001); + nv_icmd(dev, 0x0000063c, 0x00000001); + nv_icmd(dev, 0x0000063d, 0x00000002); + nv_icmd(dev, 0x0000063e, 0x00000001); + nv_icmd(dev, 0x000008b8, 0x00000001); + nv_icmd(dev, 0x000008b9, 0x00000001); + nv_icmd(dev, 0x000008ba, 0x00000001); + nv_icmd(dev, 0x000008bb, 0x00000001); + nv_icmd(dev, 0x000008bc, 0x00000001); + nv_icmd(dev, 0x000008bd, 0x00000001); + nv_icmd(dev, 0x000008be, 0x00000001); + nv_icmd(dev, 0x000008bf, 0x00000001); + nv_icmd(dev, 0x00000900, 0x00000001); + nv_icmd(dev, 0x00000901, 0x00000001); + nv_icmd(dev, 0x00000902, 0x00000001); + nv_icmd(dev, 0x00000903, 0x00000001); + nv_icmd(dev, 0x00000904, 0x00000001); + nv_icmd(dev, 0x00000905, 0x00000001); + nv_icmd(dev, 0x00000906, 0x00000001); + nv_icmd(dev, 0x00000907, 0x00000001); + nv_icmd(dev, 0x00000908, 0x00000002); + nv_icmd(dev, 0x00000909, 0x00000002); + nv_icmd(dev, 0x0000090a, 0x00000002); + nv_icmd(dev, 0x0000090b, 0x00000002); + nv_icmd(dev, 0x0000090c, 0x00000002); + nv_icmd(dev, 0x0000090d, 0x00000002); + nv_icmd(dev, 0x0000090e, 0x00000002); + nv_icmd(dev, 0x0000090f, 0x00000002); + nv_icmd(dev, 0x00000910, 0x00000001); + nv_icmd(dev, 0x00000911, 0x00000001); + nv_icmd(dev, 0x00000912, 0x00000001); + nv_icmd(dev, 0x00000913, 0x00000001); + nv_icmd(dev, 0x00000914, 0x00000001); + nv_icmd(dev, 0x00000915, 0x00000001); + nv_icmd(dev, 0x00000916, 0x00000001); + nv_icmd(dev, 0x00000917, 0x00000001); + nv_icmd(dev, 0x00000918, 0x00000001); + nv_icmd(dev, 0x00000919, 0x00000001); + nv_icmd(dev, 0x0000091a, 0x00000001); + nv_icmd(dev, 0x0000091b, 0x00000001); + nv_icmd(dev, 0x0000091c, 0x00000001); + nv_icmd(dev, 0x0000091d, 0x00000001); + nv_icmd(dev, 0x0000091e, 0x00000001); + nv_icmd(dev, 0x0000091f, 0x00000001); + nv_icmd(dev, 0x00000920, 0x00000002); + nv_icmd(dev, 0x00000921, 0x00000002); + nv_icmd(dev, 0x00000922, 0x00000002); + nv_icmd(dev, 0x00000923, 0x00000002); + nv_icmd(dev, 0x00000924, 0x00000002); + nv_icmd(dev, 0x00000925, 0x00000002); + nv_icmd(dev, 0x00000926, 0x00000002); + nv_icmd(dev, 0x00000927, 0x00000002); + nv_icmd(dev, 0x00000928, 0x00000001); + nv_icmd(dev, 0x00000929, 0x00000001); + nv_icmd(dev, 0x0000092a, 0x00000001); + nv_icmd(dev, 0x0000092b, 0x00000001); + nv_icmd(dev, 0x0000092c, 0x00000001); + nv_icmd(dev, 0x0000092d, 0x00000001); + nv_icmd(dev, 0x0000092e, 0x00000001); + nv_icmd(dev, 0x0000092f, 0x00000001); + nv_icmd(dev, 0x00000648, 0x00000001); + nv_icmd(dev, 0x00000649, 0x00000001); + nv_icmd(dev, 0x0000064a, 0x00000001); + nv_icmd(dev, 0x0000064b, 0x00000001); + nv_icmd(dev, 0x0000064c, 0x00000001); + nv_icmd(dev, 0x0000064d, 0x00000001); + nv_icmd(dev, 0x0000064e, 0x00000001); + nv_icmd(dev, 0x0000064f, 0x00000001); + nv_icmd(dev, 0x00000650, 0x00000001); + nv_icmd(dev, 0x00000658, 0x0000000f); + nv_icmd(dev, 0x000007ff, 0x0000000a); + nv_icmd(dev, 0x0000066a, 0x40000000); + nv_icmd(dev, 0x0000066b, 0x10000000); + nv_icmd(dev, 0x0000066c, 0xffff0000); + nv_icmd(dev, 0x0000066d, 0xffff0000); + nv_icmd(dev, 0x000007af, 0x00000008); + nv_icmd(dev, 0x000007b0, 0x00000008); + nv_icmd(dev, 0x000007f6, 0x00000001); + nv_icmd(dev, 0x000006b2, 0x00000055); + nv_icmd(dev, 0x000007ad, 0x00000003); + nv_icmd(dev, 0x00000937, 0x00000001); + nv_icmd(dev, 0x00000971, 0x00000008); + nv_icmd(dev, 0x00000972, 0x00000040); + nv_icmd(dev, 0x00000973, 0x0000012c); + nv_icmd(dev, 0x0000097c, 0x00000040); + nv_icmd(dev, 0x00000979, 0x00000003); + nv_icmd(dev, 0x00000975, 0x00000020); + nv_icmd(dev, 0x00000976, 0x00000001); + nv_icmd(dev, 0x00000977, 0x00000020); + nv_icmd(dev, 0x00000978, 0x00000001); + nv_icmd(dev, 0x00000957, 0x00000003); + nv_icmd(dev, 0x0000095e, 0x20164010); + nv_icmd(dev, 0x0000095f, 0x00000020); + nv_icmd(dev, 0x00000683, 0x00000006); + nv_icmd(dev, 0x00000685, 0x003fffff); + nv_icmd(dev, 0x00000687, 0x00000c48); + nv_icmd(dev, 0x000006a0, 0x00000005); + nv_icmd(dev, 0x00000840, 0x00300008); + nv_icmd(dev, 0x00000841, 0x04000080); + nv_icmd(dev, 0x00000842, 0x00300008); + nv_icmd(dev, 0x00000843, 0x04000080); + nv_icmd(dev, 0x00000818, 0x00000000); + nv_icmd(dev, 0x00000819, 0x00000000); + nv_icmd(dev, 0x0000081a, 0x00000000); + nv_icmd(dev, 0x0000081b, 0x00000000); + nv_icmd(dev, 0x0000081c, 0x00000000); + nv_icmd(dev, 0x0000081d, 0x00000000); + nv_icmd(dev, 0x0000081e, 0x00000000); + nv_icmd(dev, 0x0000081f, 0x00000000); + nv_icmd(dev, 0x00000848, 0x00000000); + nv_icmd(dev, 0x00000849, 0x00000000); + nv_icmd(dev, 0x0000084a, 0x00000000); + nv_icmd(dev, 0x0000084b, 0x00000000); + nv_icmd(dev, 0x0000084c, 0x00000000); + nv_icmd(dev, 0x0000084d, 0x00000000); + nv_icmd(dev, 0x0000084e, 0x00000000); + nv_icmd(dev, 0x0000084f, 0x00000000); + nv_icmd(dev, 0x00000850, 0x00000000); + nv_icmd(dev, 0x00000851, 0x00000000); + nv_icmd(dev, 0x00000852, 0x00000000); + nv_icmd(dev, 0x00000853, 0x00000000); + nv_icmd(dev, 0x00000854, 0x00000000); + nv_icmd(dev, 0x00000855, 0x00000000); + nv_icmd(dev, 0x00000856, 0x00000000); + nv_icmd(dev, 0x00000857, 0x00000000); + nv_icmd(dev, 0x00000738, 0x00000000); + nv_icmd(dev, 0x000006aa, 0x00000001); + nv_icmd(dev, 0x000006ab, 0x00000002); + nv_icmd(dev, 0x000006ac, 0x00000080); + nv_icmd(dev, 0x000006ad, 0x00000100); + nv_icmd(dev, 0x000006ae, 0x00000100); + nv_icmd(dev, 0x000006b1, 0x00000011); + nv_icmd(dev, 0x000006bb, 0x000000cf); + nv_icmd(dev, 0x000006ce, 0x2a712488); + nv_icmd(dev, 0x00000739, 0x4085c000); + nv_icmd(dev, 0x0000073a, 0x00000080); + nv_icmd(dev, 0x00000786, 0x80000100); + nv_icmd(dev, 0x0000073c, 0x00010100); + nv_icmd(dev, 0x0000073d, 0x02800000); + nv_icmd(dev, 0x00000787, 0x000000cf); + nv_icmd(dev, 0x0000078c, 0x00000008); + nv_icmd(dev, 0x00000792, 0x00000001); + nv_icmd(dev, 0x00000794, 0x00000001); + nv_icmd(dev, 0x00000795, 0x00000001); + nv_icmd(dev, 0x00000796, 0x00000001); + nv_icmd(dev, 0x00000797, 0x000000cf); + nv_icmd(dev, 0x00000836, 0x00000001); + nv_icmd(dev, 0x0000079a, 0x00000002); + nv_icmd(dev, 0x00000833, 0x04444480); + nv_icmd(dev, 0x000007a1, 0x00000001); + nv_icmd(dev, 0x000007a3, 0x00000001); + nv_icmd(dev, 0x000007a4, 0x00000001); + nv_icmd(dev, 0x000007a5, 0x00000001); + nv_icmd(dev, 0x00000831, 0x00000004); + nv_icmd(dev, 0x0000080c, 0x00000002); + nv_icmd(dev, 0x0000080d, 0x00000100); + nv_icmd(dev, 0x0000080e, 0x00000100); + nv_icmd(dev, 0x0000080f, 0x00000001); + nv_icmd(dev, 0x00000823, 0x00000002); + nv_icmd(dev, 0x00000824, 0x00000100); + nv_icmd(dev, 0x00000825, 0x00000100); + nv_icmd(dev, 0x00000826, 0x00000001); + nv_icmd(dev, 0x0000095d, 0x00000001); + nv_icmd(dev, 0x0000082b, 0x00000004); + nv_icmd(dev, 0x00000942, 0x00010001); + nv_icmd(dev, 0x00000943, 0x00000001); + nv_icmd(dev, 0x00000944, 0x00000022); + nv_icmd(dev, 0x000007c5, 0x00010001); + nv_icmd(dev, 0x00000834, 0x00000001); + nv_icmd(dev, 0x000007c7, 0x00000001); + nv_icmd(dev, 0x0000c1b0, 0x0000000f); + nv_icmd(dev, 0x0000c1b1, 0x0000000f); + nv_icmd(dev, 0x0000c1b2, 0x0000000f); + nv_icmd(dev, 0x0000c1b3, 0x0000000f); + nv_icmd(dev, 0x0000c1b4, 0x0000000f); + nv_icmd(dev, 0x0000c1b5, 0x0000000f); + nv_icmd(dev, 0x0000c1b6, 0x0000000f); + nv_icmd(dev, 0x0000c1b7, 0x0000000f); + nv_icmd(dev, 0x0000c1b8, 0x0fac6881); + nv_icmd(dev, 0x0000c1b9, 0x00fac688); + nv_icmd(dev, 0x0001e100, 0x00000001); + nv_icmd(dev, 0x00001000, 0x00000002); + nv_icmd(dev, 0x000006aa, 0x00000001); + nv_icmd(dev, 0x000006ad, 0x00000100); + nv_icmd(dev, 0x000006ae, 0x00000100); + nv_icmd(dev, 0x000006b1, 0x00000011); + nv_icmd(dev, 0x0000078c, 0x00000008); + nv_icmd(dev, 0x00000792, 0x00000001); + nv_icmd(dev, 0x00000794, 0x00000001); + nv_icmd(dev, 0x00000795, 0x00000001); + nv_icmd(dev, 0x00000796, 0x00000001); + nv_icmd(dev, 0x00000797, 0x000000cf); + nv_icmd(dev, 0x0000079a, 0x00000002); + nv_icmd(dev, 0x00000833, 0x04444480); + nv_icmd(dev, 0x000007a1, 0x00000001); + nv_icmd(dev, 0x000007a3, 0x00000001); + nv_icmd(dev, 0x000007a4, 0x00000001); + nv_icmd(dev, 0x000007a5, 0x00000001); + nv_icmd(dev, 0x00000831, 0x00000004); + nv_icmd(dev, 0x0001e100, 0x00000001); + nv_icmd(dev, 0x00001000, 0x00000014); + nv_icmd(dev, 0x00000351, 0x00000100); + nv_icmd(dev, 0x00000957, 0x00000003); + nv_icmd(dev, 0x0000095d, 0x00000001); + nv_icmd(dev, 0x0000082b, 0x00000004); + nv_icmd(dev, 0x00000942, 0x00010001); + nv_icmd(dev, 0x00000943, 0x00000001); + nv_icmd(dev, 0x000007c5, 0x00010001); + nv_icmd(dev, 0x00000834, 0x00000001); + nv_icmd(dev, 0x000007c7, 0x00000001); + nv_icmd(dev, 0x0001e100, 0x00000001); + nv_icmd(dev, 0x00001000, 0x00000001); + nv_icmd(dev, 0x0000080c, 0x00000002); + nv_icmd(dev, 0x0000080d, 0x00000100); + nv_icmd(dev, 0x0000080e, 0x00000100); + nv_icmd(dev, 0x0000080f, 0x00000001); + nv_icmd(dev, 0x00000823, 0x00000002); + nv_icmd(dev, 0x00000824, 0x00000100); + nv_icmd(dev, 0x00000825, 0x00000100); + nv_icmd(dev, 0x00000826, 0x00000001); + nv_icmd(dev, 0x0001e100, 0x00000001); + + nv_wr32(dev, 0x400208, 0x00000000); +} + +static void +nvc0_grctx_init_dispatch(struct drm_device *dev) +{ + int i; + + nv_wr32(dev, 0x404004, 0x00000000); + nv_wr32(dev, 0x404008, 0x00000000); + nv_wr32(dev, 0x40400c, 0x00000000); + nv_wr32(dev, 0x404010, 0x00000000); + nv_wr32(dev, 0x404014, 0x00000000); + nv_wr32(dev, 0x404018, 0x00000000); + nv_wr32(dev, 0x40401c, 0x00000000); + nv_wr32(dev, 0x404020, 0x00000000); + nv_wr32(dev, 0x404024, 0x00000000); + nv_wr32(dev, 0x404028, 0x00000000); + nv_wr32(dev, 0x40402c, 0x00000000); + nv_wr32(dev, 0x404044, 0x00000000); + nv_wr32(dev, 0x404094, 0x00000000); + nv_wr32(dev, 0x404098, 0x00000000); + nv_wr32(dev, 0x40409c, 0x00000000); + nv_wr32(dev, 0x4040a0, 0x00000000); + nv_wr32(dev, 0x4040a4, 0x00000000); + nv_wr32(dev, 0x4040a8, 0x00000000); + nv_wr32(dev, 0x4040ac, 0x00000000); + nv_wr32(dev, 0x4040b0, 0x00000000); + nv_wr32(dev, 0x4040b4, 0x00000000); + nv_wr32(dev, 0x4040b8, 0x00000000); + nv_wr32(dev, 0x4040bc, 0x00000000); + nv_wr32(dev, 0x4040c0, 0x00000000); + nv_wr32(dev, 0x4040c4, 0x00000000); + nv_wr32(dev, 0x4040c8, 0xf0000087); + nv_wr32(dev, 0x4040d0, 0x00000000); + nv_wr32(dev, 0x4040d4, 0x00000000); + nv_wr32(dev, 0x4040d8, 0x00000000); + nv_wr32(dev, 0x4040dc, 0x00000000); + nv_wr32(dev, 0x4040e0, 0x00000000); + nv_wr32(dev, 0x4040e4, 0x00000000); + nv_wr32(dev, 0x4040e8, 0x00001000); + nv_wr32(dev, 0x4040f8, 0x00000000); + nv_wr32(dev, 0x404130, 0x00000000); + nv_wr32(dev, 0x404134, 0x00000000); + nv_wr32(dev, 0x404138, 0x20000040); + nv_wr32(dev, 0x404150, 0x0000002e); + nv_wr32(dev, 0x404154, 0x00000400); + nv_wr32(dev, 0x404158, 0x00000200); + nv_wr32(dev, 0x404164, 0x00000055); + nv_wr32(dev, 0x404168, 0x00000000); + nv_wr32(dev, 0x404174, 0x00000000); + nv_wr32(dev, 0x404178, 0x00000000); + nv_wr32(dev, 0x40417c, 0x00000000); + for (i = 0; i < 8; ++i) + nv_wr32(dev, 0x404200 + i * 4, 0x00000000); /* subc */ +} + +static void +nvc0_grctx_init_macro(struct drm_device *dev) +{ + nv_wr32(dev, 0x404404, 0x00000000); + nv_wr32(dev, 0x404408, 0x00000000); + nv_wr32(dev, 0x40440c, 0x00000000); + nv_wr32(dev, 0x404410, 0x00000000); + nv_wr32(dev, 0x404414, 0x00000000); + nv_wr32(dev, 0x404418, 0x00000000); + nv_wr32(dev, 0x40441c, 0x00000000); + nv_wr32(dev, 0x404420, 0x00000000); + nv_wr32(dev, 0x404424, 0x00000000); + nv_wr32(dev, 0x404428, 0x00000000); + nv_wr32(dev, 0x40442c, 0x00000000); + nv_wr32(dev, 0x404430, 0x00000000); + nv_wr32(dev, 0x404434, 0x00000000); + nv_wr32(dev, 0x404438, 0x00000000); + nv_wr32(dev, 0x404460, 0x00000000); + nv_wr32(dev, 0x404464, 0x00000000); + nv_wr32(dev, 0x404468, 0x00ffffff); + nv_wr32(dev, 0x40446c, 0x00000000); + nv_wr32(dev, 0x404480, 0x00000001); + nv_wr32(dev, 0x404498, 0x00000001); +} + +static void +nvc0_grctx_init_m2mf(struct drm_device *dev) +{ + nv_wr32(dev, 0x404604, 0x00000015); + nv_wr32(dev, 0x404608, 0x00000000); + nv_wr32(dev, 0x40460c, 0x00002e00); + nv_wr32(dev, 0x404610, 0x00000100); + nv_wr32(dev, 0x404618, 0x00000000); + nv_wr32(dev, 0x40461c, 0x00000000); + nv_wr32(dev, 0x404620, 0x00000000); + nv_wr32(dev, 0x404624, 0x00000000); + nv_wr32(dev, 0x404628, 0x00000000); + nv_wr32(dev, 0x40462c, 0x00000000); + nv_wr32(dev, 0x404630, 0x00000000); + nv_wr32(dev, 0x404634, 0x00000000); + nv_wr32(dev, 0x404638, 0x00000004); + nv_wr32(dev, 0x40463c, 0x00000000); + nv_wr32(dev, 0x404640, 0x00000000); + nv_wr32(dev, 0x404644, 0x00000000); + nv_wr32(dev, 0x404648, 0x00000000); + nv_wr32(dev, 0x40464c, 0x00000000); + nv_wr32(dev, 0x404650, 0x00000000); + nv_wr32(dev, 0x404654, 0x00000000); + nv_wr32(dev, 0x404658, 0x00000000); + nv_wr32(dev, 0x40465c, 0x007f0100); + nv_wr32(dev, 0x404660, 0x00000000); + nv_wr32(dev, 0x404664, 0x00000000); + nv_wr32(dev, 0x404668, 0x00000000); + nv_wr32(dev, 0x40466c, 0x00000000); + nv_wr32(dev, 0x404670, 0x00000000); + nv_wr32(dev, 0x404674, 0x00000000); + nv_wr32(dev, 0x404678, 0x00000000); + nv_wr32(dev, 0x40467c, 0x00000002); + nv_wr32(dev, 0x404680, 0x00000000); + nv_wr32(dev, 0x404684, 0x00000000); + nv_wr32(dev, 0x404688, 0x00000000); + nv_wr32(dev, 0x40468c, 0x00000000); + nv_wr32(dev, 0x404690, 0x00000000); + nv_wr32(dev, 0x404694, 0x00000000); + nv_wr32(dev, 0x404698, 0x00000000); + nv_wr32(dev, 0x40469c, 0x00000000); + nv_wr32(dev, 0x4046a0, 0x007f0080); + nv_wr32(dev, 0x4046a4, 0x00000000); + nv_wr32(dev, 0x4046a8, 0x00000000); + nv_wr32(dev, 0x4046ac, 0x00000000); + nv_wr32(dev, 0x4046b0, 0x00000000); + nv_wr32(dev, 0x4046b4, 0x00000000); + nv_wr32(dev, 0x4046b8, 0x00000000); + nv_wr32(dev, 0x4046bc, 0x00000000); + nv_wr32(dev, 0x4046c0, 0x00000000); + nv_wr32(dev, 0x4046c4, 0x00000000); + nv_wr32(dev, 0x4046c8, 0x00000000); + nv_wr32(dev, 0x4046cc, 0x00000000); + nv_wr32(dev, 0x4046d0, 0x00000000); + nv_wr32(dev, 0x4046d4, 0x00000000); + nv_wr32(dev, 0x4046d8, 0x00000000); + nv_wr32(dev, 0x4046dc, 0x00000000); + nv_wr32(dev, 0x4046e0, 0x00000000); + nv_wr32(dev, 0x4046e4, 0x00000000); + nv_wr32(dev, 0x4046e8, 0x00000000); + nv_wr32(dev, 0x4046f0, 0x00000000); + nv_wr32(dev, 0x4046f4, 0x00000000); +} + +static void +nvc0_grctx_init_unk47xx(struct drm_device *dev) +{ + nv_wr32(dev, 0x404700, 0x00000000); + nv_wr32(dev, 0x404704, 0x00000000); + nv_wr32(dev, 0x404708, 0x00000000); + nv_wr32(dev, 0x40470c, 0x00000000); + nv_wr32(dev, 0x404710, 0x00000000); + nv_wr32(dev, 0x404714, 0x00000000); + nv_wr32(dev, 0x404718, 0x00000000); + nv_wr32(dev, 0x40471c, 0x00000000); + nv_wr32(dev, 0x404720, 0x00000000); + nv_wr32(dev, 0x404724, 0x00000000); + nv_wr32(dev, 0x404728, 0x00000000); + nv_wr32(dev, 0x40472c, 0x00000000); + nv_wr32(dev, 0x404730, 0x00000000); + nv_wr32(dev, 0x404734, 0x00000100); + nv_wr32(dev, 0x404738, 0x00000000); + nv_wr32(dev, 0x40473c, 0x00000000); + nv_wr32(dev, 0x404740, 0x00000000); + nv_wr32(dev, 0x404744, 0x00000000); + nv_wr32(dev, 0x404748, 0x00000000); + nv_wr32(dev, 0x40474c, 0x00000000); + nv_wr32(dev, 0x404750, 0x00000000); + nv_wr32(dev, 0x404754, 0x00000000); +} + +static void +nvc0_grctx_init_shaders(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + if (dev_priv->chipset != 0xc1) { + nv_wr32(dev, 0x405800, 0x078000bf); + nv_wr32(dev, 0x405830, 0x02180000); + } else { + nv_wr32(dev, 0x405800, 0x0f8000bf); + nv_wr32(dev, 0x405830, 0x02180218); + } + nv_wr32(dev, 0x405834, 0x00000000); + nv_wr32(dev, 0x405838, 0x00000000); + nv_wr32(dev, 0x405854, 0x00000000); + nv_wr32(dev, 0x405870, 0x00000001); + nv_wr32(dev, 0x405874, 0x00000001); + nv_wr32(dev, 0x405878, 0x00000001); + nv_wr32(dev, 0x40587c, 0x00000001); + nv_wr32(dev, 0x405a00, 0x00000000); + nv_wr32(dev, 0x405a04, 0x00000000); + nv_wr32(dev, 0x405a18, 0x00000000); +} + +static void +nvc0_grctx_init_unk60xx(struct drm_device *dev) +{ + nv_wr32(dev, 0x406020, 0x000103c1); + nv_wr32(dev, 0x406028, 0x00000001); + nv_wr32(dev, 0x40602c, 0x00000001); + nv_wr32(dev, 0x406030, 0x00000001); + nv_wr32(dev, 0x406034, 0x00000001); +} + +static void +nvc0_grctx_init_unk64xx(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + + nv_wr32(dev, 0x4064a8, 0x00000000); + nv_wr32(dev, 0x4064ac, 0x00003fff); + nv_wr32(dev, 0x4064b4, 0x00000000); + nv_wr32(dev, 0x4064b8, 0x00000000); + if (dev_priv->chipset == 0xc1) { + nv_wr32(dev, 0x4064c0, 0x80140078); + nv_wr32(dev, 0x4064c4, 0x0086ffff); + } +} + +static void +nvc0_grctx_init_tpbus(struct drm_device *dev) +{ + nv_wr32(dev, 0x407804, 0x00000023); + nv_wr32(dev, 0x40780c, 0x0a418820); + nv_wr32(dev, 0x407810, 0x062080e6); + nv_wr32(dev, 0x407814, 0x020398a4); + nv_wr32(dev, 0x407818, 0x0e629062); + nv_wr32(dev, 0x40781c, 0x0a418820); + nv_wr32(dev, 0x407820, 0x000000e6); + nv_wr32(dev, 0x4078bc, 0x00000103); +} + +static void +nvc0_grctx_init_ccache(struct drm_device *dev) +{ + nv_wr32(dev, 0x408000, 0x00000000); + nv_wr32(dev, 0x408004, 0x00000000); + nv_wr32(dev, 0x408008, 0x00000018); + nv_wr32(dev, 0x40800c, 0x00000000); + nv_wr32(dev, 0x408010, 0x00000000); + nv_wr32(dev, 0x408014, 0x00000069); + nv_wr32(dev, 0x408018, 0xe100e100); + nv_wr32(dev, 0x408064, 0x00000000); +} + +static void +nvc0_grctx_init_ropc(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int chipset = dev_priv->chipset; + + /* ROPC_BROADCAST */ + nv_wr32(dev, 0x408800, 0x02802a3c); + nv_wr32(dev, 0x408804, 0x00000040); + nv_wr32(dev, 0x408808, chipset != 0xc1 ? 0x0003e00d : 0x1003e005); + nv_wr32(dev, 0x408900, chipset != 0xc0 ? 0x3080b801 : 0x0080b801); + nv_wr32(dev, 0x408904, chipset != 0xc1 ? 0x02000001 : 0x62000001); + nv_wr32(dev, 0x408908, 0x00c80929); + nv_wr32(dev, 0x40890c, 0x00000000); + nv_wr32(dev, 0x408980, 0x0000011d); +} + +static void +nvc0_grctx_init_gpc(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int chipset = dev_priv->chipset; + int i; + + /* GPC_BROADCAST */ + nv_wr32(dev, 0x418380, 0x00000016); + nv_wr32(dev, 0x418400, 0x38004e00); + nv_wr32(dev, 0x418404, 0x71e0ffff); + nv_wr32(dev, 0x418408, 0x00000000); + nv_wr32(dev, 0x41840c, 0x00001008); + nv_wr32(dev, 0x418410, 0x0fff0fff); + nv_wr32(dev, 0x418414, 0x00200fff); + nv_wr32(dev, 0x418450, 0x00000000); + nv_wr32(dev, 0x418454, 0x00000000); + nv_wr32(dev, 0x418458, 0x00000000); + nv_wr32(dev, 0x41845c, 0x00000000); + nv_wr32(dev, 0x418460, 0x00000000); + nv_wr32(dev, 0x418464, 0x00000000); + nv_wr32(dev, 0x418468, 0x00000001); + nv_wr32(dev, 0x41846c, 0x00000000); + nv_wr32(dev, 0x418470, 0x00000000); + nv_wr32(dev, 0x418600, 0x0000001f); + nv_wr32(dev, 0x418684, 0x0000000f); + nv_wr32(dev, 0x418700, 0x00000002); + nv_wr32(dev, 0x418704, 0x00000080); + nv_wr32(dev, 0x418708, 0x00000000); + nv_wr32(dev, 0x41870c, 0x07c80000); + nv_wr32(dev, 0x418710, 0x00000000); + nv_wr32(dev, 0x418800, 0x0006860a); + nv_wr32(dev, 0x418808, 0x00000000); + nv_wr32(dev, 0x41880c, 0x00000000); + nv_wr32(dev, 0x418810, 0x00000000); + nv_wr32(dev, 0x418828, 0x00008442); + nv_wr32(dev, 0x418830, chipset != 0xc1 ? 0x00000001 : 0x10000001); + nv_wr32(dev, 0x4188d8, 0x00000008); + nv_wr32(dev, 0x4188e0, 0x01000000); + nv_wr32(dev, 0x4188e8, 0x00000000); + nv_wr32(dev, 0x4188ec, 0x00000000); + nv_wr32(dev, 0x4188f0, 0x00000000); + nv_wr32(dev, 0x4188f4, 0x00000000); + nv_wr32(dev, 0x4188f8, 0x00000000); + nv_wr32(dev, 0x4188fc, chipset != 0xc1 ? 0x00100000 : 0x00100018); + nv_wr32(dev, 0x41891c, 0x00ff00ff); + nv_wr32(dev, 0x418924, 0x00000000); + nv_wr32(dev, 0x418928, 0x00ffff00); + nv_wr32(dev, 0x41892c, 0x0000ff00); + for (i = 0; i < 8; i++) { + nv_wr32(dev, 0x418a00 + (i * 0x20), 0x00000000); + nv_wr32(dev, 0x418a04 + (i * 0x20), 0x00000000); + nv_wr32(dev, 0x418a08 + (i * 0x20), 0x00000000); + nv_wr32(dev, 0x418a0c + (i * 0x20), 0x00010000); + nv_wr32(dev, 0x418a10 + (i * 0x20), 0x00000000); + nv_wr32(dev, 0x418a14 + (i * 0x20), 0x00000000); + nv_wr32(dev, 0x418a18 + (i * 0x20), 0x00000000); + } + nv_wr32(dev, 0x418b00, 0x00000000); + nv_wr32(dev, 0x418b08, 0x0a418820); + nv_wr32(dev, 0x418b0c, 0x062080e6); + nv_wr32(dev, 0x418b10, 0x020398a4); + nv_wr32(dev, 0x418b14, 0x0e629062); + nv_wr32(dev, 0x418b18, 0x0a418820); + nv_wr32(dev, 0x418b1c, 0x000000e6); + nv_wr32(dev, 0x418bb8, 0x00000103); + nv_wr32(dev, 0x418c08, 0x00000001); + nv_wr32(dev, 0x418c10, 0x00000000); + nv_wr32(dev, 0x418c14, 0x00000000); + nv_wr32(dev, 0x418c18, 0x00000000); + nv_wr32(dev, 0x418c1c, 0x00000000); + nv_wr32(dev, 0x418c20, 0x00000000); + nv_wr32(dev, 0x418c24, 0x00000000); + nv_wr32(dev, 0x418c28, 0x00000000); + nv_wr32(dev, 0x418c2c, 0x00000000); + if (chipset == 0xc1) + nv_wr32(dev, 0x418c6c, 0x00000001); + nv_wr32(dev, 0x418c80, 0x20200004); + nv_wr32(dev, 0x418c8c, 0x00000001); + nv_wr32(dev, 0x419000, 0x00000780); + nv_wr32(dev, 0x419004, 0x00000000); + nv_wr32(dev, 0x419008, 0x00000000); + nv_wr32(dev, 0x419014, 0x00000004); +} + +static void +nvc0_grctx_init_tp(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int chipset = dev_priv->chipset; + + /* GPC_BROADCAST.TP_BROADCAST */ + nv_wr32(dev, 0x419818, 0x00000000); + nv_wr32(dev, 0x41983c, 0x00038bc7); + nv_wr32(dev, 0x419848, 0x00000000); + nv_wr32(dev, 0x419864, chipset != 0xc1 ? 0x0000012a : 0x00000129); + nv_wr32(dev, 0x419888, 0x00000000); + nv_wr32(dev, 0x419a00, 0x000001f0); + nv_wr32(dev, 0x419a04, 0x00000001); + nv_wr32(dev, 0x419a08, 0x00000023); + nv_wr32(dev, 0x419a0c, 0x00020000); + nv_wr32(dev, 0x419a10, 0x00000000); + nv_wr32(dev, 0x419a14, 0x00000200); + nv_wr32(dev, 0x419a1c, 0x00000000); + nv_wr32(dev, 0x419a20, 0x00000800); + if (chipset != 0xc0 && chipset != 0xc8) + nv_wr32(dev, 0x00419ac4, 0x0007f440); + nv_wr32(dev, 0x419b00, 0x0a418820); + nv_wr32(dev, 0x419b04, 0x062080e6); + nv_wr32(dev, 0x419b08, 0x020398a4); + nv_wr32(dev, 0x419b0c, 0x0e629062); + nv_wr32(dev, 0x419b10, 0x0a418820); + nv_wr32(dev, 0x419b14, 0x000000e6); + nv_wr32(dev, 0x419bd0, 0x00900103); + nv_wr32(dev, 0x419be0, chipset != 0xc1 ? 0x00000001 : 0x00400001); + nv_wr32(dev, 0x419be4, 0x00000000); + nv_wr32(dev, 0x419c00, 0x00000002); + nv_wr32(dev, 0x419c04, 0x00000006); + nv_wr32(dev, 0x419c08, 0x00000002); + nv_wr32(dev, 0x419c20, 0x00000000); + if (chipset == 0xce || chipset == 0xcf) + nv_wr32(dev, 0x419cb0, 0x00020048); + else + nv_wr32(dev, 0x419cb0, 0x00060048); + nv_wr32(dev, 0x419ce8, 0x00000000); + nv_wr32(dev, 0x419cf4, 0x00000183); + nv_wr32(dev, 0x419d20, chipset != 0xc1 ? 0x02180000 : 0x12180000); + nv_wr32(dev, 0x419d24, 0x00001fff); + if (chipset == 0xc1) + nv_wr32(dev, 0x419d44, 0x02180218); + nv_wr32(dev, 0x419e04, 0x00000000); + nv_wr32(dev, 0x419e08, 0x00000000); + nv_wr32(dev, 0x419e0c, 0x00000000); + nv_wr32(dev, 0x419e10, 0x00000002); + nv_wr32(dev, 0x419e44, 0x001beff2); + nv_wr32(dev, 0x419e48, 0x00000000); + nv_wr32(dev, 0x419e4c, 0x0000000f); + nv_wr32(dev, 0x419e50, 0x00000000); + nv_wr32(dev, 0x419e54, 0x00000000); + nv_wr32(dev, 0x419e58, 0x00000000); + nv_wr32(dev, 0x419e5c, 0x00000000); + nv_wr32(dev, 0x419e60, 0x00000000); + nv_wr32(dev, 0x419e64, 0x00000000); + nv_wr32(dev, 0x419e68, 0x00000000); + nv_wr32(dev, 0x419e6c, 0x00000000); + nv_wr32(dev, 0x419e70, 0x00000000); + nv_wr32(dev, 0x419e74, 0x00000000); + nv_wr32(dev, 0x419e78, 0x00000000); + nv_wr32(dev, 0x419e7c, 0x00000000); + nv_wr32(dev, 0x419e80, 0x00000000); + nv_wr32(dev, 0x419e84, 0x00000000); + nv_wr32(dev, 0x419e88, 0x00000000); + nv_wr32(dev, 0x419e8c, 0x00000000); + nv_wr32(dev, 0x419e90, 0x00000000); + nv_wr32(dev, 0x419e98, 0x00000000); + if (chipset != 0xc0 && chipset != 0xc8) + nv_wr32(dev, 0x419ee0, 0x00011110); + nv_wr32(dev, 0x419f50, 0x00000000); + nv_wr32(dev, 0x419f54, 0x00000000); + if (chipset != 0xc0 && chipset != 0xc8) + nv_wr32(dev, 0x419f58, 0x00000000); +} + +#define nv_mthd(a, c, m, d) \ + do { \ + if (data != (d)) \ + nv_wr32(dev, 0x40448c, (d)); \ + data = (d); \ + nv_wr32((a), 0x404488, (1 << 31) | ((m) << 14) | (c)); \ + } while(0) + +/* NVC0_3D */ +static void +nvc0_grctx_init_9097(struct drm_device *dev) +{ + uint32_t fermi = nvc0_graph_class(dev); + uint32_t data = ~0; + uint32_t mthd; + + nv_mthd(dev, 0x9097, 0x0800, 0x00000000); + nv_mthd(dev, 0x9097, 0x0840, 0x00000000); + nv_mthd(dev, 0x9097, 0x0880, 0x00000000); + nv_mthd(dev, 0x9097, 0x08c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0900, 0x00000000); + nv_mthd(dev, 0x9097, 0x0940, 0x00000000); + nv_mthd(dev, 0x9097, 0x0980, 0x00000000); + nv_mthd(dev, 0x9097, 0x09c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0804, 0x00000000); + nv_mthd(dev, 0x9097, 0x0844, 0x00000000); + nv_mthd(dev, 0x9097, 0x0884, 0x00000000); + nv_mthd(dev, 0x9097, 0x08c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0904, 0x00000000); + nv_mthd(dev, 0x9097, 0x0944, 0x00000000); + nv_mthd(dev, 0x9097, 0x0984, 0x00000000); + nv_mthd(dev, 0x9097, 0x09c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0808, 0x00000400); + nv_mthd(dev, 0x9097, 0x0848, 0x00000400); + nv_mthd(dev, 0x9097, 0x0888, 0x00000400); + nv_mthd(dev, 0x9097, 0x08c8, 0x00000400); + nv_mthd(dev, 0x9097, 0x0908, 0x00000400); + nv_mthd(dev, 0x9097, 0x0948, 0x00000400); + nv_mthd(dev, 0x9097, 0x0988, 0x00000400); + nv_mthd(dev, 0x9097, 0x09c8, 0x00000400); + nv_mthd(dev, 0x9097, 0x080c, 0x00000300); + nv_mthd(dev, 0x9097, 0x084c, 0x00000300); + nv_mthd(dev, 0x9097, 0x088c, 0x00000300); + nv_mthd(dev, 0x9097, 0x08cc, 0x00000300); + nv_mthd(dev, 0x9097, 0x090c, 0x00000300); + nv_mthd(dev, 0x9097, 0x094c, 0x00000300); + nv_mthd(dev, 0x9097, 0x098c, 0x00000300); + nv_mthd(dev, 0x9097, 0x09cc, 0x00000300); + nv_mthd(dev, 0x9097, 0x0810, 0x000000cf); + nv_mthd(dev, 0x9097, 0x0850, 0x00000000); + nv_mthd(dev, 0x9097, 0x0890, 0x00000000); + nv_mthd(dev, 0x9097, 0x08d0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0910, 0x00000000); + nv_mthd(dev, 0x9097, 0x0950, 0x00000000); + nv_mthd(dev, 0x9097, 0x0990, 0x00000000); + nv_mthd(dev, 0x9097, 0x09d0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0814, 0x00000040); + nv_mthd(dev, 0x9097, 0x0854, 0x00000040); + nv_mthd(dev, 0x9097, 0x0894, 0x00000040); + nv_mthd(dev, 0x9097, 0x08d4, 0x00000040); + nv_mthd(dev, 0x9097, 0x0914, 0x00000040); + nv_mthd(dev, 0x9097, 0x0954, 0x00000040); + nv_mthd(dev, 0x9097, 0x0994, 0x00000040); + nv_mthd(dev, 0x9097, 0x09d4, 0x00000040); + nv_mthd(dev, 0x9097, 0x0818, 0x00000001); + nv_mthd(dev, 0x9097, 0x0858, 0x00000001); + nv_mthd(dev, 0x9097, 0x0898, 0x00000001); + nv_mthd(dev, 0x9097, 0x08d8, 0x00000001); + nv_mthd(dev, 0x9097, 0x0918, 0x00000001); + nv_mthd(dev, 0x9097, 0x0958, 0x00000001); + nv_mthd(dev, 0x9097, 0x0998, 0x00000001); + nv_mthd(dev, 0x9097, 0x09d8, 0x00000001); + nv_mthd(dev, 0x9097, 0x081c, 0x00000000); + nv_mthd(dev, 0x9097, 0x085c, 0x00000000); + nv_mthd(dev, 0x9097, 0x089c, 0x00000000); + nv_mthd(dev, 0x9097, 0x08dc, 0x00000000); + nv_mthd(dev, 0x9097, 0x091c, 0x00000000); + nv_mthd(dev, 0x9097, 0x095c, 0x00000000); + nv_mthd(dev, 0x9097, 0x099c, 0x00000000); + nv_mthd(dev, 0x9097, 0x09dc, 0x00000000); + nv_mthd(dev, 0x9097, 0x0820, 0x00000000); + nv_mthd(dev, 0x9097, 0x0860, 0x00000000); + nv_mthd(dev, 0x9097, 0x08a0, 0x00000000); + nv_mthd(dev, 0x9097, 0x08e0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0920, 0x00000000); + nv_mthd(dev, 0x9097, 0x0960, 0x00000000); + nv_mthd(dev, 0x9097, 0x09a0, 0x00000000); + nv_mthd(dev, 0x9097, 0x09e0, 0x00000000); + nv_mthd(dev, 0x9097, 0x2700, 0x00000000); + nv_mthd(dev, 0x9097, 0x2720, 0x00000000); + nv_mthd(dev, 0x9097, 0x2740, 0x00000000); + nv_mthd(dev, 0x9097, 0x2760, 0x00000000); + nv_mthd(dev, 0x9097, 0x2780, 0x00000000); + nv_mthd(dev, 0x9097, 0x27a0, 0x00000000); + nv_mthd(dev, 0x9097, 0x27c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x27e0, 0x00000000); + nv_mthd(dev, 0x9097, 0x2704, 0x00000000); + nv_mthd(dev, 0x9097, 0x2724, 0x00000000); + nv_mthd(dev, 0x9097, 0x2744, 0x00000000); + nv_mthd(dev, 0x9097, 0x2764, 0x00000000); + nv_mthd(dev, 0x9097, 0x2784, 0x00000000); + nv_mthd(dev, 0x9097, 0x27a4, 0x00000000); + nv_mthd(dev, 0x9097, 0x27c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x27e4, 0x00000000); + nv_mthd(dev, 0x9097, 0x2708, 0x00000000); + nv_mthd(dev, 0x9097, 0x2728, 0x00000000); + nv_mthd(dev, 0x9097, 0x2748, 0x00000000); + nv_mthd(dev, 0x9097, 0x2768, 0x00000000); + nv_mthd(dev, 0x9097, 0x2788, 0x00000000); + nv_mthd(dev, 0x9097, 0x27a8, 0x00000000); + nv_mthd(dev, 0x9097, 0x27c8, 0x00000000); + nv_mthd(dev, 0x9097, 0x27e8, 0x00000000); + nv_mthd(dev, 0x9097, 0x270c, 0x00000000); + nv_mthd(dev, 0x9097, 0x272c, 0x00000000); + nv_mthd(dev, 0x9097, 0x274c, 0x00000000); + nv_mthd(dev, 0x9097, 0x276c, 0x00000000); + nv_mthd(dev, 0x9097, 0x278c, 0x00000000); + nv_mthd(dev, 0x9097, 0x27ac, 0x00000000); + nv_mthd(dev, 0x9097, 0x27cc, 0x00000000); + nv_mthd(dev, 0x9097, 0x27ec, 0x00000000); + nv_mthd(dev, 0x9097, 0x2710, 0x00014000); + nv_mthd(dev, 0x9097, 0x2730, 0x00014000); + nv_mthd(dev, 0x9097, 0x2750, 0x00014000); + nv_mthd(dev, 0x9097, 0x2770, 0x00014000); + nv_mthd(dev, 0x9097, 0x2790, 0x00014000); + nv_mthd(dev, 0x9097, 0x27b0, 0x00014000); + nv_mthd(dev, 0x9097, 0x27d0, 0x00014000); + nv_mthd(dev, 0x9097, 0x27f0, 0x00014000); + nv_mthd(dev, 0x9097, 0x2714, 0x00000040); + nv_mthd(dev, 0x9097, 0x2734, 0x00000040); + nv_mthd(dev, 0x9097, 0x2754, 0x00000040); + nv_mthd(dev, 0x9097, 0x2774, 0x00000040); + nv_mthd(dev, 0x9097, 0x2794, 0x00000040); + nv_mthd(dev, 0x9097, 0x27b4, 0x00000040); + nv_mthd(dev, 0x9097, 0x27d4, 0x00000040); + nv_mthd(dev, 0x9097, 0x27f4, 0x00000040); + nv_mthd(dev, 0x9097, 0x1c00, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c10, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c20, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c30, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c40, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c50, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c60, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c70, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c80, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c90, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ca0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cb0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cc0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cd0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ce0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cf0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c04, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c14, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c24, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c34, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c44, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c54, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c64, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c74, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c84, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c94, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ca4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cb4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cc4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cd4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ce4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cf4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c08, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c18, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c28, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c38, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c48, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c58, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c68, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c78, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c88, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c98, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ca8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cb8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cc8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cd8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ce8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cf8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c0c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c1c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c2c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c3c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c4c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c5c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c6c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c7c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c8c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1c9c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cac, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cbc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ccc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cdc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cec, 0x00000000); + nv_mthd(dev, 0x9097, 0x1cfc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d00, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d10, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d20, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d30, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d40, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d50, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d60, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d70, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d80, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d90, 0x00000000); + nv_mthd(dev, 0x9097, 0x1da0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1db0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dc0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dd0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1de0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1df0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d04, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d14, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d24, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d34, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d44, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d54, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d64, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d74, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d84, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d94, 0x00000000); + nv_mthd(dev, 0x9097, 0x1da4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1db4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dc4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dd4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1de4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1df4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d08, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d18, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d28, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d38, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d48, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d58, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d68, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d78, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d88, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d98, 0x00000000); + nv_mthd(dev, 0x9097, 0x1da8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1db8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dc8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dd8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1de8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1df8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d0c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d1c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d2c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d3c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d4c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d5c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d6c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d7c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d8c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1d9c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dac, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dbc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dcc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ddc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dec, 0x00000000); + nv_mthd(dev, 0x9097, 0x1dfc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f00, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f08, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f10, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f18, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f20, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f28, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f30, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f38, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f40, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f48, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f50, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f58, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f60, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f68, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f70, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f78, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f04, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f0c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f14, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f1c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f24, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f2c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f34, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f3c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f44, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f4c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f54, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f5c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f64, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f6c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f74, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f7c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f80, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f88, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f90, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f98, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fa0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fa8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fb0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fb8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fc0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fc8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fd0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fd8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fe0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fe8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ff0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ff8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f84, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f8c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f94, 0x00000000); + nv_mthd(dev, 0x9097, 0x1f9c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fa4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fac, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fb4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fbc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fc4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fcc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fd4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fdc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fe4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1fec, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ff4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1ffc, 0x00000000); + nv_mthd(dev, 0x9097, 0x2200, 0x00000022); + nv_mthd(dev, 0x9097, 0x2210, 0x00000022); + nv_mthd(dev, 0x9097, 0x2220, 0x00000022); + nv_mthd(dev, 0x9097, 0x2230, 0x00000022); + nv_mthd(dev, 0x9097, 0x2240, 0x00000022); + nv_mthd(dev, 0x9097, 0x2000, 0x00000000); + nv_mthd(dev, 0x9097, 0x2040, 0x00000011); + nv_mthd(dev, 0x9097, 0x2080, 0x00000020); + nv_mthd(dev, 0x9097, 0x20c0, 0x00000030); + nv_mthd(dev, 0x9097, 0x2100, 0x00000040); + nv_mthd(dev, 0x9097, 0x2140, 0x00000051); + nv_mthd(dev, 0x9097, 0x200c, 0x00000001); + nv_mthd(dev, 0x9097, 0x204c, 0x00000001); + nv_mthd(dev, 0x9097, 0x208c, 0x00000001); + nv_mthd(dev, 0x9097, 0x20cc, 0x00000001); + nv_mthd(dev, 0x9097, 0x210c, 0x00000001); + nv_mthd(dev, 0x9097, 0x214c, 0x00000001); + nv_mthd(dev, 0x9097, 0x2010, 0x00000000); + nv_mthd(dev, 0x9097, 0x2050, 0x00000000); + nv_mthd(dev, 0x9097, 0x2090, 0x00000001); + nv_mthd(dev, 0x9097, 0x20d0, 0x00000002); + nv_mthd(dev, 0x9097, 0x2110, 0x00000003); + nv_mthd(dev, 0x9097, 0x2150, 0x00000004); + nv_mthd(dev, 0x9097, 0x0380, 0x00000000); + nv_mthd(dev, 0x9097, 0x03a0, 0x00000000); + nv_mthd(dev, 0x9097, 0x03c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x03e0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0384, 0x00000000); + nv_mthd(dev, 0x9097, 0x03a4, 0x00000000); + nv_mthd(dev, 0x9097, 0x03c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x03e4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0388, 0x00000000); + nv_mthd(dev, 0x9097, 0x03a8, 0x00000000); + nv_mthd(dev, 0x9097, 0x03c8, 0x00000000); + nv_mthd(dev, 0x9097, 0x03e8, 0x00000000); + nv_mthd(dev, 0x9097, 0x038c, 0x00000000); + nv_mthd(dev, 0x9097, 0x03ac, 0x00000000); + nv_mthd(dev, 0x9097, 0x03cc, 0x00000000); + nv_mthd(dev, 0x9097, 0x03ec, 0x00000000); + nv_mthd(dev, 0x9097, 0x0700, 0x00000000); + nv_mthd(dev, 0x9097, 0x0710, 0x00000000); + nv_mthd(dev, 0x9097, 0x0720, 0x00000000); + nv_mthd(dev, 0x9097, 0x0730, 0x00000000); + nv_mthd(dev, 0x9097, 0x0704, 0x00000000); + nv_mthd(dev, 0x9097, 0x0714, 0x00000000); + nv_mthd(dev, 0x9097, 0x0724, 0x00000000); + nv_mthd(dev, 0x9097, 0x0734, 0x00000000); + nv_mthd(dev, 0x9097, 0x0708, 0x00000000); + nv_mthd(dev, 0x9097, 0x0718, 0x00000000); + nv_mthd(dev, 0x9097, 0x0728, 0x00000000); + nv_mthd(dev, 0x9097, 0x0738, 0x00000000); + nv_mthd(dev, 0x9097, 0x2800, 0x00000000); + nv_mthd(dev, 0x9097, 0x2804, 0x00000000); + nv_mthd(dev, 0x9097, 0x2808, 0x00000000); + nv_mthd(dev, 0x9097, 0x280c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2810, 0x00000000); + nv_mthd(dev, 0x9097, 0x2814, 0x00000000); + nv_mthd(dev, 0x9097, 0x2818, 0x00000000); + nv_mthd(dev, 0x9097, 0x281c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2820, 0x00000000); + nv_mthd(dev, 0x9097, 0x2824, 0x00000000); + nv_mthd(dev, 0x9097, 0x2828, 0x00000000); + nv_mthd(dev, 0x9097, 0x282c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2830, 0x00000000); + nv_mthd(dev, 0x9097, 0x2834, 0x00000000); + nv_mthd(dev, 0x9097, 0x2838, 0x00000000); + nv_mthd(dev, 0x9097, 0x283c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2840, 0x00000000); + nv_mthd(dev, 0x9097, 0x2844, 0x00000000); + nv_mthd(dev, 0x9097, 0x2848, 0x00000000); + nv_mthd(dev, 0x9097, 0x284c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2850, 0x00000000); + nv_mthd(dev, 0x9097, 0x2854, 0x00000000); + nv_mthd(dev, 0x9097, 0x2858, 0x00000000); + nv_mthd(dev, 0x9097, 0x285c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2860, 0x00000000); + nv_mthd(dev, 0x9097, 0x2864, 0x00000000); + nv_mthd(dev, 0x9097, 0x2868, 0x00000000); + nv_mthd(dev, 0x9097, 0x286c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2870, 0x00000000); + nv_mthd(dev, 0x9097, 0x2874, 0x00000000); + nv_mthd(dev, 0x9097, 0x2878, 0x00000000); + nv_mthd(dev, 0x9097, 0x287c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2880, 0x00000000); + nv_mthd(dev, 0x9097, 0x2884, 0x00000000); + nv_mthd(dev, 0x9097, 0x2888, 0x00000000); + nv_mthd(dev, 0x9097, 0x288c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2890, 0x00000000); + nv_mthd(dev, 0x9097, 0x2894, 0x00000000); + nv_mthd(dev, 0x9097, 0x2898, 0x00000000); + nv_mthd(dev, 0x9097, 0x289c, 0x00000000); + nv_mthd(dev, 0x9097, 0x28a0, 0x00000000); + nv_mthd(dev, 0x9097, 0x28a4, 0x00000000); + nv_mthd(dev, 0x9097, 0x28a8, 0x00000000); + nv_mthd(dev, 0x9097, 0x28ac, 0x00000000); + nv_mthd(dev, 0x9097, 0x28b0, 0x00000000); + nv_mthd(dev, 0x9097, 0x28b4, 0x00000000); + nv_mthd(dev, 0x9097, 0x28b8, 0x00000000); + nv_mthd(dev, 0x9097, 0x28bc, 0x00000000); + nv_mthd(dev, 0x9097, 0x28c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x28c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x28c8, 0x00000000); + nv_mthd(dev, 0x9097, 0x28cc, 0x00000000); + nv_mthd(dev, 0x9097, 0x28d0, 0x00000000); + nv_mthd(dev, 0x9097, 0x28d4, 0x00000000); + nv_mthd(dev, 0x9097, 0x28d8, 0x00000000); + nv_mthd(dev, 0x9097, 0x28dc, 0x00000000); + nv_mthd(dev, 0x9097, 0x28e0, 0x00000000); + nv_mthd(dev, 0x9097, 0x28e4, 0x00000000); + nv_mthd(dev, 0x9097, 0x28e8, 0x00000000); + nv_mthd(dev, 0x9097, 0x28ec, 0x00000000); + nv_mthd(dev, 0x9097, 0x28f0, 0x00000000); + nv_mthd(dev, 0x9097, 0x28f4, 0x00000000); + nv_mthd(dev, 0x9097, 0x28f8, 0x00000000); + nv_mthd(dev, 0x9097, 0x28fc, 0x00000000); + nv_mthd(dev, 0x9097, 0x2900, 0x00000000); + nv_mthd(dev, 0x9097, 0x2904, 0x00000000); + nv_mthd(dev, 0x9097, 0x2908, 0x00000000); + nv_mthd(dev, 0x9097, 0x290c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2910, 0x00000000); + nv_mthd(dev, 0x9097, 0x2914, 0x00000000); + nv_mthd(dev, 0x9097, 0x2918, 0x00000000); + nv_mthd(dev, 0x9097, 0x291c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2920, 0x00000000); + nv_mthd(dev, 0x9097, 0x2924, 0x00000000); + nv_mthd(dev, 0x9097, 0x2928, 0x00000000); + nv_mthd(dev, 0x9097, 0x292c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2930, 0x00000000); + nv_mthd(dev, 0x9097, 0x2934, 0x00000000); + nv_mthd(dev, 0x9097, 0x2938, 0x00000000); + nv_mthd(dev, 0x9097, 0x293c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2940, 0x00000000); + nv_mthd(dev, 0x9097, 0x2944, 0x00000000); + nv_mthd(dev, 0x9097, 0x2948, 0x00000000); + nv_mthd(dev, 0x9097, 0x294c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2950, 0x00000000); + nv_mthd(dev, 0x9097, 0x2954, 0x00000000); + nv_mthd(dev, 0x9097, 0x2958, 0x00000000); + nv_mthd(dev, 0x9097, 0x295c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2960, 0x00000000); + nv_mthd(dev, 0x9097, 0x2964, 0x00000000); + nv_mthd(dev, 0x9097, 0x2968, 0x00000000); + nv_mthd(dev, 0x9097, 0x296c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2970, 0x00000000); + nv_mthd(dev, 0x9097, 0x2974, 0x00000000); + nv_mthd(dev, 0x9097, 0x2978, 0x00000000); + nv_mthd(dev, 0x9097, 0x297c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2980, 0x00000000); + nv_mthd(dev, 0x9097, 0x2984, 0x00000000); + nv_mthd(dev, 0x9097, 0x2988, 0x00000000); + nv_mthd(dev, 0x9097, 0x298c, 0x00000000); + nv_mthd(dev, 0x9097, 0x2990, 0x00000000); + nv_mthd(dev, 0x9097, 0x2994, 0x00000000); + nv_mthd(dev, 0x9097, 0x2998, 0x00000000); + nv_mthd(dev, 0x9097, 0x299c, 0x00000000); + nv_mthd(dev, 0x9097, 0x29a0, 0x00000000); + nv_mthd(dev, 0x9097, 0x29a4, 0x00000000); + nv_mthd(dev, 0x9097, 0x29a8, 0x00000000); + nv_mthd(dev, 0x9097, 0x29ac, 0x00000000); + nv_mthd(dev, 0x9097, 0x29b0, 0x00000000); + nv_mthd(dev, 0x9097, 0x29b4, 0x00000000); + nv_mthd(dev, 0x9097, 0x29b8, 0x00000000); + nv_mthd(dev, 0x9097, 0x29bc, 0x00000000); + nv_mthd(dev, 0x9097, 0x29c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x29c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x29c8, 0x00000000); + nv_mthd(dev, 0x9097, 0x29cc, 0x00000000); + nv_mthd(dev, 0x9097, 0x29d0, 0x00000000); + nv_mthd(dev, 0x9097, 0x29d4, 0x00000000); + nv_mthd(dev, 0x9097, 0x29d8, 0x00000000); + nv_mthd(dev, 0x9097, 0x29dc, 0x00000000); + nv_mthd(dev, 0x9097, 0x29e0, 0x00000000); + nv_mthd(dev, 0x9097, 0x29e4, 0x00000000); + nv_mthd(dev, 0x9097, 0x29e8, 0x00000000); + nv_mthd(dev, 0x9097, 0x29ec, 0x00000000); + nv_mthd(dev, 0x9097, 0x29f0, 0x00000000); + nv_mthd(dev, 0x9097, 0x29f4, 0x00000000); + nv_mthd(dev, 0x9097, 0x29f8, 0x00000000); + nv_mthd(dev, 0x9097, 0x29fc, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a00, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a20, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a40, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a60, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a80, 0x00000000); + nv_mthd(dev, 0x9097, 0x0aa0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ac0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ae0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b00, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b20, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b40, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b60, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b80, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ba0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bc0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0be0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a04, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a24, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a44, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a64, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a84, 0x00000000); + nv_mthd(dev, 0x9097, 0x0aa4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ac4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ae4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b04, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b24, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b44, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b64, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b84, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ba4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bc4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0be4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a08, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a28, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a48, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a68, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a88, 0x00000000); + nv_mthd(dev, 0x9097, 0x0aa8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ac8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ae8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b08, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b28, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b48, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b68, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b88, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ba8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bc8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0be8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a0c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a2c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a4c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a6c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a8c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0aac, 0x00000000); + nv_mthd(dev, 0x9097, 0x0acc, 0x00000000); + nv_mthd(dev, 0x9097, 0x0aec, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b0c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b2c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b4c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b6c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b8c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bac, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bcc, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bec, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a10, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a30, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a50, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a70, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a90, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ab0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ad0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0af0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b10, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b30, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b50, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b70, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b90, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bb0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bd0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bf0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a14, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a34, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a54, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a74, 0x00000000); + nv_mthd(dev, 0x9097, 0x0a94, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ab4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ad4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0af4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b14, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b34, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b54, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b74, 0x00000000); + nv_mthd(dev, 0x9097, 0x0b94, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bb4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bd4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0bf4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c00, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c10, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c20, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c30, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c40, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c50, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c60, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c70, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c80, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c90, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ca0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cb0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cc0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cd0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ce0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cf0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c04, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c14, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c24, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c34, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c44, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c54, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c64, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c74, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c84, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c94, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ca4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cb4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cc4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cd4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ce4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cf4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c08, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c18, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c28, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c38, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c48, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c58, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c68, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c78, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c88, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c98, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ca8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cb8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cc8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cd8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ce8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0cf8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0c0c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0c1c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0c2c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0c3c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0c4c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0c5c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0c6c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0c7c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0c8c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0c9c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0cac, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0cbc, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0ccc, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0cdc, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0cec, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0cfc, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0d00, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d08, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d10, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d18, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d20, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d28, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d30, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d38, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d04, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d0c, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d14, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d1c, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d24, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d2c, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d34, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d3c, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e00, 0x00000000); + nv_mthd(dev, 0x9097, 0x0e10, 0x00000000); + nv_mthd(dev, 0x9097, 0x0e20, 0x00000000); + nv_mthd(dev, 0x9097, 0x0e30, 0x00000000); + nv_mthd(dev, 0x9097, 0x0e40, 0x00000000); + nv_mthd(dev, 0x9097, 0x0e50, 0x00000000); + nv_mthd(dev, 0x9097, 0x0e60, 0x00000000); + nv_mthd(dev, 0x9097, 0x0e70, 0x00000000); + nv_mthd(dev, 0x9097, 0x0e80, 0x00000000); + nv_mthd(dev, 0x9097, 0x0e90, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ea0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0eb0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ec0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ed0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ee0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ef0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0e04, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e14, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e24, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e34, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e44, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e54, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e64, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e74, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e84, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e94, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0ea4, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0eb4, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0ec4, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0ed4, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0ee4, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0ef4, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e08, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e18, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e28, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e38, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e48, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e58, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e68, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e78, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e88, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0e98, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0ea8, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0eb8, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0ec8, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0ed8, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0ee8, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0ef8, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d40, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d48, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d50, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d58, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d44, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d4c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d54, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d5c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1e00, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e20, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e40, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e60, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e80, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ea0, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ec0, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ee0, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e04, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e24, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e44, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e64, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e84, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ea4, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ec4, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ee4, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e08, 0x00000002); + nv_mthd(dev, 0x9097, 0x1e28, 0x00000002); + nv_mthd(dev, 0x9097, 0x1e48, 0x00000002); + nv_mthd(dev, 0x9097, 0x1e68, 0x00000002); + nv_mthd(dev, 0x9097, 0x1e88, 0x00000002); + nv_mthd(dev, 0x9097, 0x1ea8, 0x00000002); + nv_mthd(dev, 0x9097, 0x1ec8, 0x00000002); + nv_mthd(dev, 0x9097, 0x1ee8, 0x00000002); + nv_mthd(dev, 0x9097, 0x1e0c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e2c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e4c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e6c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e8c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1eac, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ecc, 0x00000001); + nv_mthd(dev, 0x9097, 0x1eec, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e10, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e30, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e50, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e70, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e90, 0x00000001); + nv_mthd(dev, 0x9097, 0x1eb0, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ed0, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ef0, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e14, 0x00000002); + nv_mthd(dev, 0x9097, 0x1e34, 0x00000002); + nv_mthd(dev, 0x9097, 0x1e54, 0x00000002); + nv_mthd(dev, 0x9097, 0x1e74, 0x00000002); + nv_mthd(dev, 0x9097, 0x1e94, 0x00000002); + nv_mthd(dev, 0x9097, 0x1eb4, 0x00000002); + nv_mthd(dev, 0x9097, 0x1ed4, 0x00000002); + nv_mthd(dev, 0x9097, 0x1ef4, 0x00000002); + nv_mthd(dev, 0x9097, 0x1e18, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e38, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e58, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e78, 0x00000001); + nv_mthd(dev, 0x9097, 0x1e98, 0x00000001); + nv_mthd(dev, 0x9097, 0x1eb8, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ed8, 0x00000001); + nv_mthd(dev, 0x9097, 0x1ef8, 0x00000001); + if (fermi == 0x9097) { + for (mthd = 0x3400; mthd <= 0x35fc; mthd += 4) + nv_mthd(dev, 0x9097, mthd, 0x00000000); + } + nv_mthd(dev, 0x9097, 0x3400, 0x00000000); + nv_mthd(dev, 0x9097, 0x3404, 0x00000000); + nv_mthd(dev, 0x9097, 0x3408, 0x00000000); + nv_mthd(dev, 0x9097, 0x340c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3410, 0x00000000); + nv_mthd(dev, 0x9097, 0x3414, 0x00000000); + nv_mthd(dev, 0x9097, 0x3418, 0x00000000); + nv_mthd(dev, 0x9097, 0x341c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3420, 0x00000000); + nv_mthd(dev, 0x9097, 0x3424, 0x00000000); + nv_mthd(dev, 0x9097, 0x3428, 0x00000000); + nv_mthd(dev, 0x9097, 0x342c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3430, 0x00000000); + nv_mthd(dev, 0x9097, 0x3434, 0x00000000); + nv_mthd(dev, 0x9097, 0x3438, 0x00000000); + nv_mthd(dev, 0x9097, 0x343c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3440, 0x00000000); + nv_mthd(dev, 0x9097, 0x3444, 0x00000000); + nv_mthd(dev, 0x9097, 0x3448, 0x00000000); + nv_mthd(dev, 0x9097, 0x344c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3450, 0x00000000); + nv_mthd(dev, 0x9097, 0x3454, 0x00000000); + nv_mthd(dev, 0x9097, 0x3458, 0x00000000); + nv_mthd(dev, 0x9097, 0x345c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3460, 0x00000000); + nv_mthd(dev, 0x9097, 0x3464, 0x00000000); + nv_mthd(dev, 0x9097, 0x3468, 0x00000000); + nv_mthd(dev, 0x9097, 0x346c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3470, 0x00000000); + nv_mthd(dev, 0x9097, 0x3474, 0x00000000); + nv_mthd(dev, 0x9097, 0x3478, 0x00000000); + nv_mthd(dev, 0x9097, 0x347c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3480, 0x00000000); + nv_mthd(dev, 0x9097, 0x3484, 0x00000000); + nv_mthd(dev, 0x9097, 0x3488, 0x00000000); + nv_mthd(dev, 0x9097, 0x348c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3490, 0x00000000); + nv_mthd(dev, 0x9097, 0x3494, 0x00000000); + nv_mthd(dev, 0x9097, 0x3498, 0x00000000); + nv_mthd(dev, 0x9097, 0x349c, 0x00000000); + nv_mthd(dev, 0x9097, 0x34a0, 0x00000000); + nv_mthd(dev, 0x9097, 0x34a4, 0x00000000); + nv_mthd(dev, 0x9097, 0x34a8, 0x00000000); + nv_mthd(dev, 0x9097, 0x34ac, 0x00000000); + nv_mthd(dev, 0x9097, 0x34b0, 0x00000000); + nv_mthd(dev, 0x9097, 0x34b4, 0x00000000); + nv_mthd(dev, 0x9097, 0x34b8, 0x00000000); + nv_mthd(dev, 0x9097, 0x34bc, 0x00000000); + nv_mthd(dev, 0x9097, 0x34c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x34c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x34c8, 0x00000000); + nv_mthd(dev, 0x9097, 0x34cc, 0x00000000); + nv_mthd(dev, 0x9097, 0x34d0, 0x00000000); + nv_mthd(dev, 0x9097, 0x34d4, 0x00000000); + nv_mthd(dev, 0x9097, 0x34d8, 0x00000000); + nv_mthd(dev, 0x9097, 0x34dc, 0x00000000); + nv_mthd(dev, 0x9097, 0x34e0, 0x00000000); + nv_mthd(dev, 0x9097, 0x34e4, 0x00000000); + nv_mthd(dev, 0x9097, 0x34e8, 0x00000000); + nv_mthd(dev, 0x9097, 0x34ec, 0x00000000); + nv_mthd(dev, 0x9097, 0x34f0, 0x00000000); + nv_mthd(dev, 0x9097, 0x34f4, 0x00000000); + nv_mthd(dev, 0x9097, 0x34f8, 0x00000000); + nv_mthd(dev, 0x9097, 0x34fc, 0x00000000); + nv_mthd(dev, 0x9097, 0x3500, 0x00000000); + nv_mthd(dev, 0x9097, 0x3504, 0x00000000); + nv_mthd(dev, 0x9097, 0x3508, 0x00000000); + nv_mthd(dev, 0x9097, 0x350c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3510, 0x00000000); + nv_mthd(dev, 0x9097, 0x3514, 0x00000000); + nv_mthd(dev, 0x9097, 0x3518, 0x00000000); + nv_mthd(dev, 0x9097, 0x351c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3520, 0x00000000); + nv_mthd(dev, 0x9097, 0x3524, 0x00000000); + nv_mthd(dev, 0x9097, 0x3528, 0x00000000); + nv_mthd(dev, 0x9097, 0x352c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3530, 0x00000000); + nv_mthd(dev, 0x9097, 0x3534, 0x00000000); + nv_mthd(dev, 0x9097, 0x3538, 0x00000000); + nv_mthd(dev, 0x9097, 0x353c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3540, 0x00000000); + nv_mthd(dev, 0x9097, 0x3544, 0x00000000); + nv_mthd(dev, 0x9097, 0x3548, 0x00000000); + nv_mthd(dev, 0x9097, 0x354c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3550, 0x00000000); + nv_mthd(dev, 0x9097, 0x3554, 0x00000000); + nv_mthd(dev, 0x9097, 0x3558, 0x00000000); + nv_mthd(dev, 0x9097, 0x355c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3560, 0x00000000); + nv_mthd(dev, 0x9097, 0x3564, 0x00000000); + nv_mthd(dev, 0x9097, 0x3568, 0x00000000); + nv_mthd(dev, 0x9097, 0x356c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3570, 0x00000000); + nv_mthd(dev, 0x9097, 0x3574, 0x00000000); + nv_mthd(dev, 0x9097, 0x3578, 0x00000000); + nv_mthd(dev, 0x9097, 0x357c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3580, 0x00000000); + nv_mthd(dev, 0x9097, 0x3584, 0x00000000); + nv_mthd(dev, 0x9097, 0x3588, 0x00000000); + nv_mthd(dev, 0x9097, 0x358c, 0x00000000); + nv_mthd(dev, 0x9097, 0x3590, 0x00000000); + nv_mthd(dev, 0x9097, 0x3594, 0x00000000); + nv_mthd(dev, 0x9097, 0x3598, 0x00000000); + nv_mthd(dev, 0x9097, 0x359c, 0x00000000); + nv_mthd(dev, 0x9097, 0x35a0, 0x00000000); + nv_mthd(dev, 0x9097, 0x35a4, 0x00000000); + nv_mthd(dev, 0x9097, 0x35a8, 0x00000000); + nv_mthd(dev, 0x9097, 0x35ac, 0x00000000); + nv_mthd(dev, 0x9097, 0x35b0, 0x00000000); + nv_mthd(dev, 0x9097, 0x35b4, 0x00000000); + nv_mthd(dev, 0x9097, 0x35b8, 0x00000000); + nv_mthd(dev, 0x9097, 0x35bc, 0x00000000); + nv_mthd(dev, 0x9097, 0x35c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x35c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x35c8, 0x00000000); + nv_mthd(dev, 0x9097, 0x35cc, 0x00000000); + nv_mthd(dev, 0x9097, 0x35d0, 0x00000000); + nv_mthd(dev, 0x9097, 0x35d4, 0x00000000); + nv_mthd(dev, 0x9097, 0x35d8, 0x00000000); + nv_mthd(dev, 0x9097, 0x35dc, 0x00000000); + nv_mthd(dev, 0x9097, 0x35e0, 0x00000000); + nv_mthd(dev, 0x9097, 0x35e4, 0x00000000); + nv_mthd(dev, 0x9097, 0x35e8, 0x00000000); + nv_mthd(dev, 0x9097, 0x35ec, 0x00000000); + nv_mthd(dev, 0x9097, 0x35f0, 0x00000000); + nv_mthd(dev, 0x9097, 0x35f4, 0x00000000); + nv_mthd(dev, 0x9097, 0x35f8, 0x00000000); + nv_mthd(dev, 0x9097, 0x35fc, 0x00000000); + nv_mthd(dev, 0x9097, 0x030c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1944, 0x00000000); + nv_mthd(dev, 0x9097, 0x1514, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d68, 0x0000ffff); + nv_mthd(dev, 0x9097, 0x121c, 0x0fac6881); + nv_mthd(dev, 0x9097, 0x0fac, 0x00000001); + nv_mthd(dev, 0x9097, 0x1538, 0x00000001); + nv_mthd(dev, 0x9097, 0x0fe0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0fe4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0fe8, 0x00000014); + nv_mthd(dev, 0x9097, 0x0fec, 0x00000040); + nv_mthd(dev, 0x9097, 0x0ff0, 0x00000000); + nv_mthd(dev, 0x9097, 0x179c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1228, 0x00000400); + nv_mthd(dev, 0x9097, 0x122c, 0x00000300); + nv_mthd(dev, 0x9097, 0x1230, 0x00010001); + nv_mthd(dev, 0x9097, 0x07f8, 0x00000000); + nv_mthd(dev, 0x9097, 0x15b4, 0x00000001); + nv_mthd(dev, 0x9097, 0x15cc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1534, 0x00000000); + nv_mthd(dev, 0x9097, 0x0fb0, 0x00000000); + nv_mthd(dev, 0x9097, 0x15d0, 0x00000000); + nv_mthd(dev, 0x9097, 0x153c, 0x00000000); + nv_mthd(dev, 0x9097, 0x16b4, 0x00000003); + nv_mthd(dev, 0x9097, 0x0fbc, 0x0000ffff); + nv_mthd(dev, 0x9097, 0x0fc0, 0x0000ffff); + nv_mthd(dev, 0x9097, 0x0fc4, 0x0000ffff); + nv_mthd(dev, 0x9097, 0x0fc8, 0x0000ffff); + nv_mthd(dev, 0x9097, 0x0df8, 0x00000000); + nv_mthd(dev, 0x9097, 0x0dfc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1948, 0x00000000); + nv_mthd(dev, 0x9097, 0x1970, 0x00000001); + nv_mthd(dev, 0x9097, 0x161c, 0x000009f0); + nv_mthd(dev, 0x9097, 0x0dcc, 0x00000010); + nv_mthd(dev, 0x9097, 0x163c, 0x00000000); + nv_mthd(dev, 0x9097, 0x15e4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1160, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1164, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1168, 0x25e00040); + nv_mthd(dev, 0x9097, 0x116c, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1170, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1174, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1178, 0x25e00040); + nv_mthd(dev, 0x9097, 0x117c, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1180, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1184, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1188, 0x25e00040); + nv_mthd(dev, 0x9097, 0x118c, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1190, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1194, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1198, 0x25e00040); + nv_mthd(dev, 0x9097, 0x119c, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11a0, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11a4, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11a8, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11ac, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11b0, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11b4, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11b8, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11bc, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11c0, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11c4, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11c8, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11cc, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11d0, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11d4, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11d8, 0x25e00040); + nv_mthd(dev, 0x9097, 0x11dc, 0x25e00040); + nv_mthd(dev, 0x9097, 0x1880, 0x00000000); + nv_mthd(dev, 0x9097, 0x1884, 0x00000000); + nv_mthd(dev, 0x9097, 0x1888, 0x00000000); + nv_mthd(dev, 0x9097, 0x188c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1890, 0x00000000); + nv_mthd(dev, 0x9097, 0x1894, 0x00000000); + nv_mthd(dev, 0x9097, 0x1898, 0x00000000); + nv_mthd(dev, 0x9097, 0x189c, 0x00000000); + nv_mthd(dev, 0x9097, 0x18a0, 0x00000000); + nv_mthd(dev, 0x9097, 0x18a4, 0x00000000); + nv_mthd(dev, 0x9097, 0x18a8, 0x00000000); + nv_mthd(dev, 0x9097, 0x18ac, 0x00000000); + nv_mthd(dev, 0x9097, 0x18b0, 0x00000000); + nv_mthd(dev, 0x9097, 0x18b4, 0x00000000); + nv_mthd(dev, 0x9097, 0x18b8, 0x00000000); + nv_mthd(dev, 0x9097, 0x18bc, 0x00000000); + nv_mthd(dev, 0x9097, 0x18c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x18c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x18c8, 0x00000000); + nv_mthd(dev, 0x9097, 0x18cc, 0x00000000); + nv_mthd(dev, 0x9097, 0x18d0, 0x00000000); + nv_mthd(dev, 0x9097, 0x18d4, 0x00000000); + nv_mthd(dev, 0x9097, 0x18d8, 0x00000000); + nv_mthd(dev, 0x9097, 0x18dc, 0x00000000); + nv_mthd(dev, 0x9097, 0x18e0, 0x00000000); + nv_mthd(dev, 0x9097, 0x18e4, 0x00000000); + nv_mthd(dev, 0x9097, 0x18e8, 0x00000000); + nv_mthd(dev, 0x9097, 0x18ec, 0x00000000); + nv_mthd(dev, 0x9097, 0x18f0, 0x00000000); + nv_mthd(dev, 0x9097, 0x18f4, 0x00000000); + nv_mthd(dev, 0x9097, 0x18f8, 0x00000000); + nv_mthd(dev, 0x9097, 0x18fc, 0x00000000); + nv_mthd(dev, 0x9097, 0x0f84, 0x00000000); + nv_mthd(dev, 0x9097, 0x0f88, 0x00000000); + nv_mthd(dev, 0x9097, 0x17c8, 0x00000000); + nv_mthd(dev, 0x9097, 0x17cc, 0x00000000); + nv_mthd(dev, 0x9097, 0x17d0, 0x000000ff); + nv_mthd(dev, 0x9097, 0x17d4, 0xffffffff); + nv_mthd(dev, 0x9097, 0x17d8, 0x00000002); + nv_mthd(dev, 0x9097, 0x17dc, 0x00000000); + nv_mthd(dev, 0x9097, 0x15f4, 0x00000000); + nv_mthd(dev, 0x9097, 0x15f8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1434, 0x00000000); + nv_mthd(dev, 0x9097, 0x1438, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d74, 0x00000000); + nv_mthd(dev, 0x9097, 0x0dec, 0x00000001); + nv_mthd(dev, 0x9097, 0x13a4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1318, 0x00000001); + nv_mthd(dev, 0x9097, 0x1644, 0x00000000); + nv_mthd(dev, 0x9097, 0x0748, 0x00000000); + nv_mthd(dev, 0x9097, 0x0de8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1648, 0x00000000); + nv_mthd(dev, 0x9097, 0x12a4, 0x00000000); + nv_mthd(dev, 0x9097, 0x1120, 0x00000000); + nv_mthd(dev, 0x9097, 0x1124, 0x00000000); + nv_mthd(dev, 0x9097, 0x1128, 0x00000000); + nv_mthd(dev, 0x9097, 0x112c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1118, 0x00000000); + nv_mthd(dev, 0x9097, 0x164c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1658, 0x00000000); + nv_mthd(dev, 0x9097, 0x1910, 0x00000290); + nv_mthd(dev, 0x9097, 0x1518, 0x00000000); + nv_mthd(dev, 0x9097, 0x165c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1520, 0x00000000); + nv_mthd(dev, 0x9097, 0x1604, 0x00000000); + nv_mthd(dev, 0x9097, 0x1570, 0x00000000); + nv_mthd(dev, 0x9097, 0x13b0, 0x3f800000); + nv_mthd(dev, 0x9097, 0x13b4, 0x3f800000); + nv_mthd(dev, 0x9097, 0x020c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1670, 0x30201000); + nv_mthd(dev, 0x9097, 0x1674, 0x70605040); + nv_mthd(dev, 0x9097, 0x1678, 0xb8a89888); + nv_mthd(dev, 0x9097, 0x167c, 0xf8e8d8c8); + nv_mthd(dev, 0x9097, 0x166c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1680, 0x00ffff00); + nv_mthd(dev, 0x9097, 0x12d0, 0x00000003); + nv_mthd(dev, 0x9097, 0x12d4, 0x00000002); + nv_mthd(dev, 0x9097, 0x1684, 0x00000000); + nv_mthd(dev, 0x9097, 0x1688, 0x00000000); + nv_mthd(dev, 0x9097, 0x0dac, 0x00001b02); + nv_mthd(dev, 0x9097, 0x0db0, 0x00001b02); + nv_mthd(dev, 0x9097, 0x0db4, 0x00000000); + nv_mthd(dev, 0x9097, 0x168c, 0x00000000); + nv_mthd(dev, 0x9097, 0x15bc, 0x00000000); + nv_mthd(dev, 0x9097, 0x156c, 0x00000000); + nv_mthd(dev, 0x9097, 0x187c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1110, 0x00000001); + nv_mthd(dev, 0x9097, 0x0dc0, 0x00000000); + nv_mthd(dev, 0x9097, 0x0dc4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0dc8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1234, 0x00000000); + nv_mthd(dev, 0x9097, 0x1690, 0x00000000); + nv_mthd(dev, 0x9097, 0x12ac, 0x00000001); + nv_mthd(dev, 0x9097, 0x02c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0790, 0x00000000); + nv_mthd(dev, 0x9097, 0x0794, 0x00000000); + nv_mthd(dev, 0x9097, 0x0798, 0x00000000); + nv_mthd(dev, 0x9097, 0x079c, 0x00000000); + nv_mthd(dev, 0x9097, 0x07a0, 0x00000000); + nv_mthd(dev, 0x9097, 0x077c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1000, 0x00000010); + nv_mthd(dev, 0x9097, 0x10fc, 0x00000000); + nv_mthd(dev, 0x9097, 0x1290, 0x00000000); + nv_mthd(dev, 0x9097, 0x0218, 0x00000010); + nv_mthd(dev, 0x9097, 0x12d8, 0x00000000); + nv_mthd(dev, 0x9097, 0x12dc, 0x00000010); + nv_mthd(dev, 0x9097, 0x0d94, 0x00000001); + nv_mthd(dev, 0x9097, 0x155c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1560, 0x00000000); + nv_mthd(dev, 0x9097, 0x1564, 0x00001fff); + nv_mthd(dev, 0x9097, 0x1574, 0x00000000); + nv_mthd(dev, 0x9097, 0x1578, 0x00000000); + nv_mthd(dev, 0x9097, 0x157c, 0x003fffff); + nv_mthd(dev, 0x9097, 0x1354, 0x00000000); + nv_mthd(dev, 0x9097, 0x1664, 0x00000000); + nv_mthd(dev, 0x9097, 0x1610, 0x00000012); + nv_mthd(dev, 0x9097, 0x1608, 0x00000000); + nv_mthd(dev, 0x9097, 0x160c, 0x00000000); + nv_mthd(dev, 0x9097, 0x162c, 0x00000003); + nv_mthd(dev, 0x9097, 0x0210, 0x00000000); + nv_mthd(dev, 0x9097, 0x0320, 0x00000000); + nv_mthd(dev, 0x9097, 0x0324, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0328, 0x3f800000); + nv_mthd(dev, 0x9097, 0x032c, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0330, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0334, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0338, 0x3f800000); + nv_mthd(dev, 0x9097, 0x0750, 0x00000000); + nv_mthd(dev, 0x9097, 0x0760, 0x39291909); + nv_mthd(dev, 0x9097, 0x0764, 0x79695949); + nv_mthd(dev, 0x9097, 0x0768, 0xb9a99989); + nv_mthd(dev, 0x9097, 0x076c, 0xf9e9d9c9); + nv_mthd(dev, 0x9097, 0x0770, 0x30201000); + nv_mthd(dev, 0x9097, 0x0774, 0x70605040); + nv_mthd(dev, 0x9097, 0x0778, 0x00009080); + nv_mthd(dev, 0x9097, 0x0780, 0x39291909); + nv_mthd(dev, 0x9097, 0x0784, 0x79695949); + nv_mthd(dev, 0x9097, 0x0788, 0xb9a99989); + nv_mthd(dev, 0x9097, 0x078c, 0xf9e9d9c9); + nv_mthd(dev, 0x9097, 0x07d0, 0x30201000); + nv_mthd(dev, 0x9097, 0x07d4, 0x70605040); + nv_mthd(dev, 0x9097, 0x07d8, 0x00009080); + nv_mthd(dev, 0x9097, 0x037c, 0x00000001); + nv_mthd(dev, 0x9097, 0x0740, 0x00000000); + nv_mthd(dev, 0x9097, 0x0744, 0x00000000); + nv_mthd(dev, 0x9097, 0x2600, 0x00000000); + nv_mthd(dev, 0x9097, 0x1918, 0x00000000); + nv_mthd(dev, 0x9097, 0x191c, 0x00000900); + nv_mthd(dev, 0x9097, 0x1920, 0x00000405); + nv_mthd(dev, 0x9097, 0x1308, 0x00000001); + nv_mthd(dev, 0x9097, 0x1924, 0x00000000); + nv_mthd(dev, 0x9097, 0x13ac, 0x00000000); + nv_mthd(dev, 0x9097, 0x192c, 0x00000001); + nv_mthd(dev, 0x9097, 0x193c, 0x00002c1c); + nv_mthd(dev, 0x9097, 0x0d7c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0f8c, 0x00000000); + nv_mthd(dev, 0x9097, 0x02c0, 0x00000001); + nv_mthd(dev, 0x9097, 0x1510, 0x00000000); + nv_mthd(dev, 0x9097, 0x1940, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ff4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0ff8, 0x00000000); + nv_mthd(dev, 0x9097, 0x194c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1950, 0x00000000); + nv_mthd(dev, 0x9097, 0x1968, 0x00000000); + nv_mthd(dev, 0x9097, 0x1590, 0x0000003f); + nv_mthd(dev, 0x9097, 0x07e8, 0x00000000); + nv_mthd(dev, 0x9097, 0x07ec, 0x00000000); + nv_mthd(dev, 0x9097, 0x07f0, 0x00000000); + nv_mthd(dev, 0x9097, 0x07f4, 0x00000000); + nv_mthd(dev, 0x9097, 0x196c, 0x00000011); + nv_mthd(dev, 0x9097, 0x197c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0fcc, 0x00000000); + nv_mthd(dev, 0x9097, 0x0fd0, 0x00000000); + nv_mthd(dev, 0x9097, 0x02d8, 0x00000040); + nv_mthd(dev, 0x9097, 0x1980, 0x00000080); + nv_mthd(dev, 0x9097, 0x1504, 0x00000080); + nv_mthd(dev, 0x9097, 0x1984, 0x00000000); + nv_mthd(dev, 0x9097, 0x0300, 0x00000001); + nv_mthd(dev, 0x9097, 0x13a8, 0x00000000); + nv_mthd(dev, 0x9097, 0x12ec, 0x00000000); + nv_mthd(dev, 0x9097, 0x1310, 0x00000000); + nv_mthd(dev, 0x9097, 0x1314, 0x00000001); + nv_mthd(dev, 0x9097, 0x1380, 0x00000000); + nv_mthd(dev, 0x9097, 0x1384, 0x00000001); + nv_mthd(dev, 0x9097, 0x1388, 0x00000001); + nv_mthd(dev, 0x9097, 0x138c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1390, 0x00000001); + nv_mthd(dev, 0x9097, 0x1394, 0x00000000); + nv_mthd(dev, 0x9097, 0x139c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1398, 0x00000000); + nv_mthd(dev, 0x9097, 0x1594, 0x00000000); + nv_mthd(dev, 0x9097, 0x1598, 0x00000001); + nv_mthd(dev, 0x9097, 0x159c, 0x00000001); + nv_mthd(dev, 0x9097, 0x15a0, 0x00000001); + nv_mthd(dev, 0x9097, 0x15a4, 0x00000001); + nv_mthd(dev, 0x9097, 0x0f54, 0x00000000); + nv_mthd(dev, 0x9097, 0x0f58, 0x00000000); + nv_mthd(dev, 0x9097, 0x0f5c, 0x00000000); + nv_mthd(dev, 0x9097, 0x19bc, 0x00000000); + nv_mthd(dev, 0x9097, 0x0f9c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0fa0, 0x00000000); + nv_mthd(dev, 0x9097, 0x12cc, 0x00000000); + nv_mthd(dev, 0x9097, 0x12e8, 0x00000000); + nv_mthd(dev, 0x9097, 0x130c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1360, 0x00000000); + nv_mthd(dev, 0x9097, 0x1364, 0x00000000); + nv_mthd(dev, 0x9097, 0x1368, 0x00000000); + nv_mthd(dev, 0x9097, 0x136c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1370, 0x00000000); + nv_mthd(dev, 0x9097, 0x1374, 0x00000000); + nv_mthd(dev, 0x9097, 0x1378, 0x00000000); + nv_mthd(dev, 0x9097, 0x137c, 0x00000000); + nv_mthd(dev, 0x9097, 0x133c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1340, 0x00000001); + nv_mthd(dev, 0x9097, 0x1344, 0x00000002); + nv_mthd(dev, 0x9097, 0x1348, 0x00000001); + nv_mthd(dev, 0x9097, 0x134c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1350, 0x00000002); + nv_mthd(dev, 0x9097, 0x1358, 0x00000001); + nv_mthd(dev, 0x9097, 0x12e4, 0x00000000); + nv_mthd(dev, 0x9097, 0x131c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1320, 0x00000000); + nv_mthd(dev, 0x9097, 0x1324, 0x00000000); + nv_mthd(dev, 0x9097, 0x1328, 0x00000000); + nv_mthd(dev, 0x9097, 0x19c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1140, 0x00000000); + nv_mthd(dev, 0x9097, 0x19c4, 0x00000000); + nv_mthd(dev, 0x9097, 0x19c8, 0x00001500); + nv_mthd(dev, 0x9097, 0x135c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0f90, 0x00000000); + nv_mthd(dev, 0x9097, 0x19e0, 0x00000001); + nv_mthd(dev, 0x9097, 0x19e4, 0x00000001); + nv_mthd(dev, 0x9097, 0x19e8, 0x00000001); + nv_mthd(dev, 0x9097, 0x19ec, 0x00000001); + nv_mthd(dev, 0x9097, 0x19f0, 0x00000001); + nv_mthd(dev, 0x9097, 0x19f4, 0x00000001); + nv_mthd(dev, 0x9097, 0x19f8, 0x00000001); + nv_mthd(dev, 0x9097, 0x19fc, 0x00000001); + nv_mthd(dev, 0x9097, 0x19cc, 0x00000001); + nv_mthd(dev, 0x9097, 0x15b8, 0x00000000); + nv_mthd(dev, 0x9097, 0x1a00, 0x00001111); + nv_mthd(dev, 0x9097, 0x1a04, 0x00000000); + nv_mthd(dev, 0x9097, 0x1a08, 0x00000000); + nv_mthd(dev, 0x9097, 0x1a0c, 0x00000000); + nv_mthd(dev, 0x9097, 0x1a10, 0x00000000); + nv_mthd(dev, 0x9097, 0x1a14, 0x00000000); + nv_mthd(dev, 0x9097, 0x1a18, 0x00000000); + nv_mthd(dev, 0x9097, 0x1a1c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d6c, 0xffff0000); + nv_mthd(dev, 0x9097, 0x0d70, 0xffff0000); + nv_mthd(dev, 0x9097, 0x10f8, 0x00001010); + nv_mthd(dev, 0x9097, 0x0d80, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d84, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d88, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d8c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0d90, 0x00000000); + nv_mthd(dev, 0x9097, 0x0da0, 0x00000000); + nv_mthd(dev, 0x9097, 0x1508, 0x80000000); + nv_mthd(dev, 0x9097, 0x150c, 0x40000000); + nv_mthd(dev, 0x9097, 0x1668, 0x00000000); + nv_mthd(dev, 0x9097, 0x0318, 0x00000008); + nv_mthd(dev, 0x9097, 0x031c, 0x00000008); + nv_mthd(dev, 0x9097, 0x0d9c, 0x00000001); + nv_mthd(dev, 0x9097, 0x07dc, 0x00000000); + nv_mthd(dev, 0x9097, 0x074c, 0x00000055); + nv_mthd(dev, 0x9097, 0x1420, 0x00000003); + nv_mthd(dev, 0x9097, 0x17bc, 0x00000000); + nv_mthd(dev, 0x9097, 0x17c0, 0x00000000); + nv_mthd(dev, 0x9097, 0x17c4, 0x00000001); + nv_mthd(dev, 0x9097, 0x1008, 0x00000008); + nv_mthd(dev, 0x9097, 0x100c, 0x00000040); + nv_mthd(dev, 0x9097, 0x1010, 0x0000012c); + nv_mthd(dev, 0x9097, 0x0d60, 0x00000040); + nv_mthd(dev, 0x9097, 0x075c, 0x00000003); + nv_mthd(dev, 0x9097, 0x1018, 0x00000020); + nv_mthd(dev, 0x9097, 0x101c, 0x00000001); + nv_mthd(dev, 0x9097, 0x1020, 0x00000020); + nv_mthd(dev, 0x9097, 0x1024, 0x00000001); + nv_mthd(dev, 0x9097, 0x1444, 0x00000000); + nv_mthd(dev, 0x9097, 0x1448, 0x00000000); + nv_mthd(dev, 0x9097, 0x144c, 0x00000000); + nv_mthd(dev, 0x9097, 0x0360, 0x20164010); + nv_mthd(dev, 0x9097, 0x0364, 0x00000020); + nv_mthd(dev, 0x9097, 0x0368, 0x00000000); + nv_mthd(dev, 0x9097, 0x0de4, 0x00000000); + nv_mthd(dev, 0x9097, 0x0204, 0x00000006); + nv_mthd(dev, 0x9097, 0x0208, 0x00000000); + nv_mthd(dev, 0x9097, 0x02cc, 0x003fffff); + nv_mthd(dev, 0x9097, 0x02d0, 0x00000c48); + nv_mthd(dev, 0x9097, 0x1220, 0x00000005); + nv_mthd(dev, 0x9097, 0x0fdc, 0x00000000); + nv_mthd(dev, 0x9097, 0x0f98, 0x00300008); + nv_mthd(dev, 0x9097, 0x1284, 0x04000080); + nv_mthd(dev, 0x9097, 0x1450, 0x00300008); + nv_mthd(dev, 0x9097, 0x1454, 0x04000080); + nv_mthd(dev, 0x9097, 0x0214, 0x00000000); + /* in trace, right after 0x90c0, not here */ + nv_mthd(dev, 0x9097, 0x3410, 0x80002006); +} + +static void +nvc0_grctx_init_9197(struct drm_device *dev) +{ + uint32_t fermi = nvc0_graph_class(dev); + uint32_t data = ~0; + uint32_t mthd; + + if (fermi == 0x9197) { + for (mthd = 0x3400; mthd <= 0x35fc; mthd += 4) + nv_mthd(dev, 0x9197, mthd, 0x00000000); + } + nv_mthd(dev, 0x9197, 0x02e4, 0x0000b001); +} + +static void +nvc0_grctx_init_9297(struct drm_device *dev) +{ + uint32_t fermi = nvc0_graph_class(dev); + uint32_t data = ~0; + uint32_t mthd; + + if (fermi == 0x9297) { + for (mthd = 0x3400; mthd <= 0x35fc; mthd += 4) + nv_mthd(dev, 0x9297, mthd, 0x00000000); + } + nv_mthd(dev, 0x9297, 0x036c, 0x00000000); + nv_mthd(dev, 0x9297, 0x0370, 0x00000000); + nv_mthd(dev, 0x9297, 0x07a4, 0x00000000); + nv_mthd(dev, 0x9297, 0x07a8, 0x00000000); + nv_mthd(dev, 0x9297, 0x0374, 0x00000000); + nv_mthd(dev, 0x9297, 0x0378, 0x00000020); +} + +/* NVC0_2D */ +static void +nvc0_grctx_init_902d(struct drm_device *dev) +{ + uint32_t data = ~0; + + nv_mthd(dev, 0x902d, 0x0200, 0x000000cf); + nv_mthd(dev, 0x902d, 0x0204, 0x00000001); + nv_mthd(dev, 0x902d, 0x0208, 0x00000020); + nv_mthd(dev, 0x902d, 0x020c, 0x00000001); + nv_mthd(dev, 0x902d, 0x0210, 0x00000000); + nv_mthd(dev, 0x902d, 0x0214, 0x00000080); + nv_mthd(dev, 0x902d, 0x0218, 0x00000100); + nv_mthd(dev, 0x902d, 0x021c, 0x00000100); + nv_mthd(dev, 0x902d, 0x0220, 0x00000000); + nv_mthd(dev, 0x902d, 0x0224, 0x00000000); + nv_mthd(dev, 0x902d, 0x0230, 0x000000cf); + nv_mthd(dev, 0x902d, 0x0234, 0x00000001); + nv_mthd(dev, 0x902d, 0x0238, 0x00000020); + nv_mthd(dev, 0x902d, 0x023c, 0x00000001); + nv_mthd(dev, 0x902d, 0x0244, 0x00000080); + nv_mthd(dev, 0x902d, 0x0248, 0x00000100); + nv_mthd(dev, 0x902d, 0x024c, 0x00000100); +} + +/* NVC0_M2MF */ +static void +nvc0_grctx_init_9039(struct drm_device *dev) +{ + uint32_t data = ~0; + + nv_mthd(dev, 0x9039, 0x030c, 0x00000000); + nv_mthd(dev, 0x9039, 0x0310, 0x00000000); + nv_mthd(dev, 0x9039, 0x0314, 0x00000000); + nv_mthd(dev, 0x9039, 0x0320, 0x00000000); + nv_mthd(dev, 0x9039, 0x0238, 0x00000000); + nv_mthd(dev, 0x9039, 0x023c, 0x00000000); + nv_mthd(dev, 0x9039, 0x0318, 0x00000000); + nv_mthd(dev, 0x9039, 0x031c, 0x00000000); +} + +/* NVC0_COMPUTE */ +static void +nvc0_grctx_init_90c0(struct drm_device *dev) +{ + uint32_t data = ~0; + + nv_mthd(dev, 0x90c0, 0x270c, 0x00000000); + nv_mthd(dev, 0x90c0, 0x272c, 0x00000000); + nv_mthd(dev, 0x90c0, 0x274c, 0x00000000); + nv_mthd(dev, 0x90c0, 0x276c, 0x00000000); + nv_mthd(dev, 0x90c0, 0x278c, 0x00000000); + nv_mthd(dev, 0x90c0, 0x27ac, 0x00000000); + nv_mthd(dev, 0x90c0, 0x27cc, 0x00000000); + nv_mthd(dev, 0x90c0, 0x27ec, 0x00000000); + nv_mthd(dev, 0x90c0, 0x030c, 0x00000001); + nv_mthd(dev, 0x90c0, 0x1944, 0x00000000); + nv_mthd(dev, 0x90c0, 0x0758, 0x00000100); + nv_mthd(dev, 0x90c0, 0x02c4, 0x00000000); + nv_mthd(dev, 0x90c0, 0x0790, 0x00000000); + nv_mthd(dev, 0x90c0, 0x0794, 0x00000000); + nv_mthd(dev, 0x90c0, 0x0798, 0x00000000); + nv_mthd(dev, 0x90c0, 0x079c, 0x00000000); + nv_mthd(dev, 0x90c0, 0x07a0, 0x00000000); + nv_mthd(dev, 0x90c0, 0x077c, 0x00000000); + nv_mthd(dev, 0x90c0, 0x0204, 0x00000000); + nv_mthd(dev, 0x90c0, 0x0208, 0x00000000); + nv_mthd(dev, 0x90c0, 0x020c, 0x00000000); + nv_mthd(dev, 0x90c0, 0x0214, 0x00000000); + nv_mthd(dev, 0x90c0, 0x024c, 0x00000000); + nv_mthd(dev, 0x90c0, 0x0d94, 0x00000001); + nv_mthd(dev, 0x90c0, 0x1608, 0x00000000); + nv_mthd(dev, 0x90c0, 0x160c, 0x00000000); + nv_mthd(dev, 0x90c0, 0x1664, 0x00000000); +} diff --git a/driver/pscnv/nvc0_grgpc.fuc b/driver/pscnv/nvc0_grgpc.fuc new file mode 100644 index 00000000..a9e93c80 --- /dev/null +++ b/driver/pscnv/nvc0_grgpc.fuc @@ -0,0 +1,480 @@ +/* fuc microcode for nvc0 PGRAPH/GPC + * + * Copyright 2011 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +/* To build: + * m4 nvc0_grgpc.fuc | envyas -a -w -m fuc -V nva3 -o nvc0_grgpc.fuc.h + */ + +/* TODO + * - bracket certain functions with scratch writes, useful for debugging + * - watchdog timer around ctx operations + */ + +.section #nvc0_grgpc_data +include(`nvc0_graph.fuc') +gpc_id: .b32 0 +gpc_mmio_list_head: .b32 0 +gpc_mmio_list_tail: .b32 0 + +tpc_count: .b32 0 +tpc_mask: .b32 0 +tpc_mmio_list_head: .b32 0 +tpc_mmio_list_tail: .b32 0 + +cmd_queue: queue_init + +// chipset descriptions +chipsets: +.b8 0xc0 0 0 0 +.b16 #nvc0_gpc_mmio_head +.b16 #nvc0_gpc_mmio_tail +.b16 #nvc0_tpc_mmio_head +.b16 #nvc0_tpc_mmio_tail +.b8 0xc1 0 0 0 +.b16 #nvc0_gpc_mmio_head +.b16 #nvc1_gpc_mmio_tail +.b16 #nvc0_tpc_mmio_head +.b16 #nvc1_tpc_mmio_tail +.b8 0xc3 0 0 0 +.b16 #nvc0_gpc_mmio_head +.b16 #nvc0_gpc_mmio_tail +.b16 #nvc0_tpc_mmio_head +.b16 #nvc3_tpc_mmio_tail +.b8 0xc4 0 0 0 +.b16 #nvc0_gpc_mmio_head +.b16 #nvc0_gpc_mmio_tail +.b16 #nvc0_tpc_mmio_head +.b16 #nvc3_tpc_mmio_tail +.b8 0xc8 0 0 0 +.b16 #nvc0_gpc_mmio_head +.b16 #nvc0_gpc_mmio_tail +.b16 #nvc0_tpc_mmio_head +.b16 #nvc0_tpc_mmio_tail +.b8 0xce 0 0 0 +.b16 #nvc0_gpc_mmio_head +.b16 #nvc0_gpc_mmio_tail +.b16 #nvc0_tpc_mmio_head +.b16 #nvc3_tpc_mmio_tail +.b8 0xcf 0 0 0 +.b16 #nvc0_gpc_mmio_head +.b16 #nvc0_gpc_mmio_tail +.b16 #nvc0_tpc_mmio_head +.b16 #nvcf_tpc_mmio_tail +.b8 0 0 0 0 + +// GPC mmio lists +nvc0_gpc_mmio_head: +mmctx_data(0x000380, 1) +mmctx_data(0x000400, 6) +mmctx_data(0x000450, 9) +mmctx_data(0x000600, 1) +mmctx_data(0x000684, 1) +mmctx_data(0x000700, 5) +mmctx_data(0x000800, 1) +mmctx_data(0x000808, 3) +mmctx_data(0x000828, 1) +mmctx_data(0x000830, 1) +mmctx_data(0x0008d8, 1) +mmctx_data(0x0008e0, 1) +mmctx_data(0x0008e8, 6) +mmctx_data(0x00091c, 1) +mmctx_data(0x000924, 3) +mmctx_data(0x000b00, 1) +mmctx_data(0x000b08, 6) +mmctx_data(0x000bb8, 1) +mmctx_data(0x000c08, 1) +mmctx_data(0x000c10, 8) +mmctx_data(0x000c80, 1) +mmctx_data(0x000c8c, 1) +mmctx_data(0x001000, 3) +mmctx_data(0x001014, 1) +nvc0_gpc_mmio_tail: +mmctx_data(0x000c6c, 1); +nvc1_gpc_mmio_tail: + +// TPC mmio lists +nvc0_tpc_mmio_head: +mmctx_data(0x000018, 1) +mmctx_data(0x00003c, 1) +mmctx_data(0x000048, 1) +mmctx_data(0x000064, 1) +mmctx_data(0x000088, 1) +mmctx_data(0x000200, 6) +mmctx_data(0x00021c, 2) +mmctx_data(0x000300, 6) +mmctx_data(0x0003d0, 1) +mmctx_data(0x0003e0, 2) +mmctx_data(0x000400, 3) +mmctx_data(0x000420, 1) +mmctx_data(0x0004b0, 1) +mmctx_data(0x0004e8, 1) +mmctx_data(0x0004f4, 1) +mmctx_data(0x000520, 2) +mmctx_data(0x000604, 4) +mmctx_data(0x000644, 20) +mmctx_data(0x000698, 1) +mmctx_data(0x000750, 2) +nvc0_tpc_mmio_tail: +mmctx_data(0x000758, 1) +mmctx_data(0x0002c4, 1) +mmctx_data(0x0006e0, 1) +nvcf_tpc_mmio_tail: +mmctx_data(0x0004bc, 1) +nvc3_tpc_mmio_tail: +mmctx_data(0x000544, 1) +nvc1_tpc_mmio_tail: + + +.section #nvc0_grgpc_code +bra #init +define(`include_code') +include(`nvc0_graph.fuc') + +// reports an exception to the host +// +// In: $r15 error code (see nvc0_graph.fuc) +// +error: + push $r14 + mov $r14 -0x67ec // 0x9814 + sethi $r14 0x400000 + call #nv_wr32 // HUB_CTXCTL_CC_SCRATCH[5] = error code + add b32 $r14 0x41c + mov $r15 1 + call #nv_wr32 // HUB_CTXCTL_INTR_UP_SET + pop $r14 + ret + +// GPC fuc initialisation, executed by triggering ucode start, will +// fall through to main loop after completion. +// +// Input: +// CC_SCRATCH[0]: chipset (PMC_BOOT_0 read returns 0x0bad0bad... sigh) +// CC_SCRATCH[1]: context base +// +// Output: +// CC_SCRATCH[0]: +// 31:31: set to signal completion +// CC_SCRATCH[1]: +// 31:0: GPC context size +// +init: + clear b32 $r0 + mov $sp $r0 + + // enable fifo access + mov $r1 0x1200 + mov $r2 2 + iowr I[$r1 + 0x000] $r2 // FIFO_ENABLE + + // setup i0 handler, and route all interrupts to it + mov $r1 #ih + mov $iv0 $r1 + mov $r1 0x400 + iowr I[$r1 + 0x300] $r0 // INTR_DISPATCH + + // enable fifo interrupt + mov $r2 4 + iowr I[$r1 + 0x000] $r2 // INTR_EN_SET + + // enable interrupts + bset $flags ie0 + + // figure out which GPC we are, and how many TPCs we have + mov $r1 0x608 + shl b32 $r1 6 + iord $r2 I[$r1 + 0x000] // UNITS + mov $r3 1 + and $r2 0x1f + shl b32 $r3 $r2 + sub b32 $r3 1 + st b32 D[$r0 + #tpc_count] $r2 + st b32 D[$r0 + #tpc_mask] $r3 + add b32 $r1 0x400 + iord $r2 I[$r1 + 0x000] // MYINDEX + st b32 D[$r0 + #gpc_id] $r2 + + // find context data for this chipset + mov $r2 0x800 + shl b32 $r2 6 + iord $r2 I[$r2 + 0x000] // CC_SCRATCH[0] + mov $r1 #chipsets - 12 + init_find_chipset: + add b32 $r1 12 + ld b32 $r3 D[$r1 + 0x00] + cmpu b32 $r3 $r2 + bra e #init_context + cmpu b32 $r3 0 + bra ne #init_find_chipset + // unknown chipset + ret + + // initialise context base, and size tracking + init_context: + mov $r2 0x800 + shl b32 $r2 6 + iord $r2 I[$r2 + 0x100] // CC_SCRATCH[1], initial base + clear b32 $r3 // track GPC context size here + + // set mmctx base addresses now so we don't have to do it later, + // they don't currently ever change + mov $r4 0x700 + shl b32 $r4 6 + shr b32 $r5 $r2 8 + iowr I[$r4 + 0x000] $r5 // MMCTX_SAVE_SWBASE + iowr I[$r4 + 0x100] $r5 // MMCTX_LOAD_SWBASE + + // calculate GPC mmio context size, store the chipset-specific + // mmio list pointers somewhere we can get at them later without + // re-parsing the chipset list + clear b32 $r14 + clear b32 $r15 + ld b16 $r14 D[$r1 + 4] + ld b16 $r15 D[$r1 + 6] + st b16 D[$r0 + #gpc_mmio_list_head] $r14 + st b16 D[$r0 + #gpc_mmio_list_tail] $r15 + call #mmctx_size + add b32 $r2 $r15 + add b32 $r3 $r15 + + // calculate per-TPC mmio context size, store the list pointers + ld b16 $r14 D[$r1 + 8] + ld b16 $r15 D[$r1 + 10] + st b16 D[$r0 + #tpc_mmio_list_head] $r14 + st b16 D[$r0 + #tpc_mmio_list_tail] $r15 + call #mmctx_size + ld b32 $r14 D[$r0 + #tpc_count] + mulu $r14 $r15 + add b32 $r2 $r14 + add b32 $r3 $r14 + + // round up base/size to 256 byte boundary (for strand SWBASE) + add b32 $r4 0x1300 + shr b32 $r3 2 + iowr I[$r4 + 0x000] $r3 // MMCTX_LOAD_COUNT, wtf for?!? + shr b32 $r2 8 + shr b32 $r3 6 + add b32 $r2 1 + add b32 $r3 1 + shl b32 $r2 8 + shl b32 $r3 8 + + // calculate size of strand context data + mov b32 $r15 $r2 + call #strand_ctx_init + add b32 $r3 $r15 + + // save context size, and tell HUB we're done + mov $r1 0x800 + shl b32 $r1 6 + iowr I[$r1 + 0x100] $r3 // CC_SCRATCH[1] = context size + add b32 $r1 0x800 + clear b32 $r2 + bset $r2 31 + iowr I[$r1 + 0x000] $r2 // CC_SCRATCH[0] |= 0x80000000 + +// Main program loop, very simple, sleeps until woken up by the interrupt +// handler, pulls a command from the queue and executes its handler +// +main: + bset $flags $p0 + sleep $p0 + mov $r13 #cmd_queue + call #queue_get + bra $p1 #main + + // 0x0000-0x0003 are all context transfers + cmpu b32 $r14 0x04 + bra nc #main_not_ctx_xfer + // fetch $flags and mask off $p1/$p2 + mov $r1 $flags + mov $r2 0x0006 + not b32 $r2 + and $r1 $r2 + // set $p1/$p2 according to transfer type + shl b32 $r14 1 + or $r1 $r14 + mov $flags $r1 + // transfer context data + call #ctx_xfer + bra #main + + main_not_ctx_xfer: + shl b32 $r15 $r14 16 + or $r15 E_BAD_COMMAND + call #error + bra #main + +// interrupt handler +ih: + push $r8 + mov $r8 $flags + push $r8 + push $r9 + push $r10 + push $r11 + push $r13 + push $r14 + push $r15 + + // incoming fifo command? + iord $r10 I[$r0 + 0x200] // INTR + and $r11 $r10 0x00000004 + bra e #ih_no_fifo + // queue incoming fifo command for later processing + mov $r11 0x1900 + mov $r13 #cmd_queue + iord $r14 I[$r11 + 0x100] // FIFO_CMD + iord $r15 I[$r11 + 0x000] // FIFO_DATA + call #queue_put + add b32 $r11 0x400 + mov $r14 1 + iowr I[$r11 + 0x000] $r14 // FIFO_ACK + + // ack, and wake up main() + ih_no_fifo: + iowr I[$r0 + 0x100] $r10 // INTR_ACK + + pop $r15 + pop $r14 + pop $r13 + pop $r11 + pop $r10 + pop $r9 + pop $r8 + mov $flags $r8 + pop $r8 + bclr $flags $p0 + iret + +// Set this GPC's bit in HUB_BAR, used to signal completion of various +// activities to the HUB fuc +// +hub_barrier_done: + mov $r15 1 + ld b32 $r14 D[$r0 + #gpc_id] + shl b32 $r15 $r14 + mov $r14 -0x6be8 // 0x409418 - HUB_BAR_SET + sethi $r14 0x400000 + call #nv_wr32 + ret + +// Disables various things, waits a bit, and re-enables them.. +// +// Not sure how exactly this helps, perhaps "ENABLE" is not such a +// good description for the bits we turn off? Anyways, without this, +// funny things happen. +// +ctx_redswitch: + mov $r14 0x614 + shl b32 $r14 6 + mov $r15 0x020 + iowr I[$r14] $r15 // GPC_RED_SWITCH = POWER + mov $r15 8 + ctx_redswitch_delay: + sub b32 $r15 1 + bra ne #ctx_redswitch_delay + mov $r15 0xa20 + iowr I[$r14] $r15 // GPC_RED_SWITCH = UNK11, ENABLE, POWER + ret + +// Transfer GPC context data between GPU and storage area +// +// In: $r15 context base address +// $p1 clear on save, set on load +// $p2 set if opposite direction done/will be done, so: +// on save it means: "a load will follow this save" +// on load it means: "a save preceeded this load" +// +ctx_xfer: + // set context base address + mov $r1 0xa04 + shl b32 $r1 6 + iowr I[$r1 + 0x000] $r15// MEM_BASE + bra not $p1 #ctx_xfer_not_load + call #ctx_redswitch + ctx_xfer_not_load: + + // strands + mov $r1 0x4afc + sethi $r1 0x20000 + mov $r2 0xc + iowr I[$r1] $r2 // STRAND_CMD(0x3f) = 0x0c + call #strand_wait + mov $r2 0x47fc + sethi $r2 0x20000 + iowr I[$r2] $r0 // STRAND_FIRST_GENE(0x3f) = 0x00 + xbit $r2 $flags $p1 + add b32 $r2 3 + iowr I[$r1] $r2 // STRAND_CMD(0x3f) = 0x03/0x04 (SAVE/LOAD) + + // mmio context + xbit $r10 $flags $p1 // direction + or $r10 2 // first + mov $r11 0x0000 + sethi $r11 0x500000 + ld b32 $r12 D[$r0 + #gpc_id] + shl b32 $r12 15 + add b32 $r11 $r12 // base = NV_PGRAPH_GPCn + ld b32 $r12 D[$r0 + #gpc_mmio_list_head] + ld b32 $r13 D[$r0 + #gpc_mmio_list_tail] + mov $r14 0 // not multi + call #mmctx_xfer + + // per-TPC mmio context + xbit $r10 $flags $p1 // direction + or $r10 4 // last + mov $r11 0x4000 + sethi $r11 0x500000 // base = NV_PGRAPH_GPC0_TPC0 + ld b32 $r12 D[$r0 + #gpc_id] + shl b32 $r12 15 + add b32 $r11 $r12 // base = NV_PGRAPH_GPCn_TPC0 + ld b32 $r12 D[$r0 + #tpc_mmio_list_head] + ld b32 $r13 D[$r0 + #tpc_mmio_list_tail] + ld b32 $r15 D[$r0 + #tpc_mask] + mov $r14 0x800 // stride = 0x800 + call #mmctx_xfer + + // wait for strands to finish + call #strand_wait + + // if load, or a save without a load following, do some + // unknown stuff that's done after finishing a block of + // strand commands + bra $p1 #ctx_xfer_post + bra not $p2 #ctx_xfer_done + ctx_xfer_post: + mov $r1 0x4afc + sethi $r1 0x20000 + mov $r2 0xd + iowr I[$r1] $r2 // STRAND_CMD(0x3f) = 0x0d + call #strand_wait + + // mark completion in HUB's barrier + ctx_xfer_done: + call #hub_barrier_done + ret + +.align 256 diff --git a/driver/pscnv/nvc0_grhub.fuc b/driver/pscnv/nvc0_grhub.fuc new file mode 100644 index 00000000..3ea31966 --- /dev/null +++ b/driver/pscnv/nvc0_grhub.fuc @@ -0,0 +1,811 @@ +/* fuc microcode for nvc0 PGRAPH/HUB + * + * Copyright 2011 Red Hat Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Ben Skeggs + */ + +/* To build: + * m4 nvc0_grhub.fuc | envyas -a -w -m fuc -V nva3 -o nvc0_grhub.fuc.h + */ + +.section #nvc0_grhub_data +include(`nvc0_graph.fuc') +gpc_count: .b32 0 +rop_count: .b32 0 +cmd_queue: queue_init +hub_mmio_list_head: .b32 0 +hub_mmio_list_tail: .b32 0 + +ctx_current: .b32 0 + +chipsets: +.b8 0xc0 0 0 0 +.b16 #nvc0_hub_mmio_head +.b16 #nvc0_hub_mmio_tail +.b8 0xc1 0 0 0 +.b16 #nvc0_hub_mmio_head +.b16 #nvc1_hub_mmio_tail +.b8 0xc3 0 0 0 +.b16 #nvc0_hub_mmio_head +.b16 #nvc0_hub_mmio_tail +.b8 0xc4 0 0 0 +.b16 #nvc0_hub_mmio_head +.b16 #nvc0_hub_mmio_tail +.b8 0xc8 0 0 0 +.b16 #nvc0_hub_mmio_head +.b16 #nvc0_hub_mmio_tail +.b8 0xce 0 0 0 +.b16 #nvc0_hub_mmio_head +.b16 #nvc0_hub_mmio_tail +.b8 0xcf 0 0 0 +.b16 #nvc0_hub_mmio_head +.b16 #nvc0_hub_mmio_tail +.b8 0 0 0 0 + +nvc0_hub_mmio_head: +mmctx_data(0x17e91c, 2) +mmctx_data(0x400204, 2) +mmctx_data(0x404004, 11) +mmctx_data(0x404044, 1) +mmctx_data(0x404094, 14) +mmctx_data(0x4040d0, 7) +mmctx_data(0x4040f8, 1) +mmctx_data(0x404130, 3) +mmctx_data(0x404150, 3) +mmctx_data(0x404164, 2) +mmctx_data(0x404174, 3) +mmctx_data(0x404200, 8) +mmctx_data(0x404404, 14) +mmctx_data(0x404460, 4) +mmctx_data(0x404480, 1) +mmctx_data(0x404498, 1) +mmctx_data(0x404604, 4) +mmctx_data(0x404618, 32) +mmctx_data(0x404698, 21) +mmctx_data(0x4046f0, 2) +mmctx_data(0x404700, 22) +mmctx_data(0x405800, 1) +mmctx_data(0x405830, 3) +mmctx_data(0x405854, 1) +mmctx_data(0x405870, 4) +mmctx_data(0x405a00, 2) +mmctx_data(0x405a18, 1) +mmctx_data(0x406020, 1) +mmctx_data(0x406028, 4) +mmctx_data(0x4064a8, 2) +mmctx_data(0x4064b4, 2) +mmctx_data(0x407804, 1) +mmctx_data(0x40780c, 6) +mmctx_data(0x4078bc, 1) +mmctx_data(0x408000, 7) +mmctx_data(0x408064, 1) +mmctx_data(0x408800, 3) +mmctx_data(0x408900, 4) +mmctx_data(0x408980, 1) +nvc0_hub_mmio_tail: +mmctx_data(0x4064c0, 2) +nvc1_hub_mmio_tail: + +.align 256 +chan_data: +chan_mmio_count: .b32 0 +chan_mmio_address: .b32 0 + +.align 256 +xfer_data: .b32 0 + +.section #nvc0_grhub_code +bra #init +define(`include_code') +include(`nvc0_graph.fuc') + +// reports an exception to the host +// +// In: $r15 error code (see nvc0_graph.fuc) +// +error: + push $r14 + mov $r14 0x814 + shl b32 $r14 6 + iowr I[$r14 + 0x000] $r15 // CC_SCRATCH[5] = error code + mov $r14 0xc1c + shl b32 $r14 6 + mov $r15 1 + iowr I[$r14 + 0x000] $r15 // INTR_UP_SET + pop $r14 + ret + +// HUB fuc initialisation, executed by triggering ucode start, will +// fall through to main loop after completion. +// +// Input: +// CC_SCRATCH[0]: chipset (PMC_BOOT_0 read returns 0x0bad0bad... sigh) +// +// Output: +// CC_SCRATCH[0]: +// 31:31: set to signal completion +// CC_SCRATCH[1]: +// 31:0: total PGRAPH context size +// +init: + clear b32 $r0 + mov $sp $r0 + mov $xdbase $r0 + + // enable fifo access + mov $r1 0x1200 + mov $r2 2 + iowr I[$r1 + 0x000] $r2 // FIFO_ENABLE + + // setup i0 handler, and route all interrupts to it + mov $r1 #ih + mov $iv0 $r1 + mov $r1 0x400 + iowr I[$r1 + 0x300] $r0 // INTR_DISPATCH + + // route HUB_CHANNEL_SWITCH to fuc interrupt 8 + mov $r3 0x404 + shl b32 $r3 6 + mov $r2 0x2003 // { HUB_CHANNEL_SWITCH, ZERO } -> intr 8 + iowr I[$r3 + 0x000] $r2 + + // not sure what these are, route them because NVIDIA does, and + // the IRQ handler will signal the host if we ever get one.. we + // may find out if/why we need to handle these if so.. + // + mov $r2 0x2004 + iowr I[$r3 + 0x004] $r2 // { 0x04, ZERO } -> intr 9 + mov $r2 0x200b + iowr I[$r3 + 0x008] $r2 // { 0x0b, ZERO } -> intr 10 + mov $r2 0x200c + iowr I[$r3 + 0x01c] $r2 // { 0x0c, ZERO } -> intr 15 + + // enable all INTR_UP interrupts + mov $r2 0xc24 + shl b32 $r2 6 + not b32 $r3 $r0 + iowr I[$r2] $r3 + + // enable fifo, ctxsw, 9, 10, 15 interrupts + mov $r2 -0x78fc // 0x8704 + sethi $r2 0 + iowr I[$r1 + 0x000] $r2 // INTR_EN_SET + + // fifo level triggered, rest edge + sub b32 $r1 0x100 + mov $r2 4 + iowr I[$r1] $r2 + + // enable interrupts + bset $flags ie0 + + // fetch enabled GPC/ROP counts + mov $r14 -0x69fc // 0x409604 + sethi $r14 0x400000 + call #nv_rd32 + extr $r1 $r15 16:20 + st b32 D[$r0 + #rop_count] $r1 + and $r15 0x1f + st b32 D[$r0 + #gpc_count] $r15 + + // set BAR_REQMASK to GPC mask + mov $r1 1 + shl b32 $r1 $r15 + sub b32 $r1 1 + mov $r2 0x40c + shl b32 $r2 6 + iowr I[$r2 + 0x000] $r1 + iowr I[$r2 + 0x100] $r1 + + // find context data for this chipset + mov $r2 0x800 + shl b32 $r2 6 + iord $r2 I[$r2 + 0x000] // CC_SCRATCH[0] + mov $r15 #chipsets - 8 + init_find_chipset: + add b32 $r15 8 + ld b32 $r3 D[$r15 + 0x00] + cmpu b32 $r3 $r2 + bra e #init_context + cmpu b32 $r3 0 + bra ne #init_find_chipset + // unknown chipset + ret + + // context size calculation, reserve first 256 bytes for use by fuc + init_context: + mov $r1 256 + + // calculate size of mmio context data + ld b16 $r14 D[$r15 + 4] + ld b16 $r15 D[$r15 + 6] + sethi $r14 0 + st b32 D[$r0 + #hub_mmio_list_head] $r14 + st b32 D[$r0 + #hub_mmio_list_tail] $r15 + call #mmctx_size + + // set mmctx base addresses now so we don't have to do it later, + // they don't (currently) ever change + mov $r3 0x700 + shl b32 $r3 6 + shr b32 $r4 $r1 8 + iowr I[$r3 + 0x000] $r4 // MMCTX_SAVE_SWBASE + iowr I[$r3 + 0x100] $r4 // MMCTX_LOAD_SWBASE + add b32 $r3 0x1300 + add b32 $r1 $r15 + shr b32 $r15 2 + iowr I[$r3 + 0x000] $r15 // MMCTX_LOAD_COUNT, wtf for?!? + + // strands, base offset needs to be aligned to 256 bytes + shr b32 $r1 8 + add b32 $r1 1 + shl b32 $r1 8 + mov b32 $r15 $r1 + call #strand_ctx_init + add b32 $r1 $r15 + + // initialise each GPC in sequence by passing in the offset of its + // context data in GPCn_CC_SCRATCH[1], and starting its FUC (which + // has previously been uploaded by the host) running. + // + // the GPC fuc init sequence will set GPCn_CC_SCRATCH[0] bit 31 + // when it has completed, and return the size of its context data + // in GPCn_CC_SCRATCH[1] + // + ld b32 $r3 D[$r0 + #gpc_count] + mov $r4 0x2000 + sethi $r4 0x500000 + init_gpc: + // setup, and start GPC ucode running + add b32 $r14 $r4 0x804 + mov b32 $r15 $r1 + call #nv_wr32 // CC_SCRATCH[1] = ctx offset + add b32 $r14 $r4 0x800 + mov b32 $r15 $r2 + call #nv_wr32 // CC_SCRATCH[0] = chipset + add b32 $r14 $r4 0x10c + clear b32 $r15 + call #nv_wr32 + add b32 $r14 $r4 0x104 + call #nv_wr32 // ENTRY + add b32 $r14 $r4 0x100 + mov $r15 2 // CTRL_START_TRIGGER + call #nv_wr32 // CTRL + + // wait for it to complete, and adjust context size + add b32 $r14 $r4 0x800 + init_gpc_wait: + call #nv_rd32 + xbit $r15 $r15 31 + bra e #init_gpc_wait + add b32 $r14 $r4 0x804 + call #nv_rd32 + add b32 $r1 $r15 + + // next! + add b32 $r4 0x8000 + sub b32 $r3 1 + bra ne #init_gpc + + // save context size, and tell host we're ready + mov $r2 0x800 + shl b32 $r2 6 + iowr I[$r2 + 0x100] $r1 // CC_SCRATCH[1] = context size + add b32 $r2 0x800 + clear b32 $r1 + bset $r1 31 + iowr I[$r2 + 0x000] $r1 // CC_SCRATCH[0] |= 0x80000000 + +// Main program loop, very simple, sleeps until woken up by the interrupt +// handler, pulls a command from the queue and executes its handler +// +main: + // sleep until we have something to do + bset $flags $p0 + sleep $p0 + mov $r13 #cmd_queue + call #queue_get + bra $p1 #main + + // context switch, requested by GPU? + cmpu b32 $r14 0x4001 + bra ne #main_not_ctx_switch + trace_set(T_AUTO) + mov $r1 0xb00 + shl b32 $r1 6 + iord $r2 I[$r1 + 0x100] // CHAN_NEXT + iord $r1 I[$r1 + 0x000] // CHAN_CUR + + xbit $r3 $r1 31 + bra e #chsw_no_prev + xbit $r3 $r2 31 + bra e #chsw_prev_no_next + push $r2 + mov b32 $r2 $r1 + trace_set(T_SAVE) + bclr $flags $p1 + bset $flags $p2 + call #ctx_xfer + trace_clr(T_SAVE); + pop $r2 + trace_set(T_LOAD); + bset $flags $p1 + call #ctx_xfer + trace_clr(T_LOAD); + bra #chsw_done + chsw_prev_no_next: + push $r2 + mov b32 $r2 $r1 + bclr $flags $p1 + bclr $flags $p2 + call #ctx_xfer + pop $r2 + mov $r1 0xb00 + shl b32 $r1 6 + iowr I[$r1] $r2 + bra #chsw_done + chsw_no_prev: + xbit $r3 $r2 31 + bra e #chsw_done + bset $flags $p1 + bclr $flags $p2 + call #ctx_xfer + + // ack the context switch request + chsw_done: + mov $r1 0xb0c + shl b32 $r1 6 + mov $r2 1 + iowr I[$r1 + 0x000] $r2 // 0x409b0c + trace_clr(T_AUTO) + bra #main + + // request to set current channel? (*not* a context switch) + main_not_ctx_switch: + cmpu b32 $r14 0x0001 + bra ne #main_not_ctx_chan + mov b32 $r2 $r15 + call #ctx_chan + bra #main_done + + // request to store current channel context? + main_not_ctx_chan: + cmpu b32 $r14 0x0002 + bra ne #main_not_ctx_save + trace_set(T_SAVE) + bclr $flags $p1 + bclr $flags $p2 + call #ctx_xfer + trace_clr(T_SAVE) + bra #main_done + + main_not_ctx_save: + shl b32 $r15 $r14 16 + or $r15 E_BAD_COMMAND + call #error + bra #main + + main_done: + mov $r1 0x820 + shl b32 $r1 6 + clear b32 $r2 + bset $r2 31 + iowr I[$r1 + 0x000] $r2 // CC_SCRATCH[0] |= 0x80000000 + bra #main + +// interrupt handler +ih: + push $r8 + mov $r8 $flags + push $r8 + push $r9 + push $r10 + push $r11 + push $r13 + push $r14 + push $r15 + + // incoming fifo command? + iord $r10 I[$r0 + 0x200] // INTR + and $r11 $r10 0x00000004 + bra e #ih_no_fifo + // queue incoming fifo command for later processing + mov $r11 0x1900 + mov $r13 #cmd_queue + iord $r14 I[$r11 + 0x100] // FIFO_CMD + iord $r15 I[$r11 + 0x000] // FIFO_DATA + call #queue_put + add b32 $r11 0x400 + mov $r14 1 + iowr I[$r11 + 0x000] $r14 // FIFO_ACK + + // context switch request? + ih_no_fifo: + and $r11 $r10 0x00000100 + bra e #ih_no_ctxsw + // enqueue a context switch for later processing + mov $r13 #cmd_queue + mov $r14 0x4001 + call #queue_put + + // anything we didn't handle, bring it to the host's attention + ih_no_ctxsw: + mov $r11 0x104 + not b32 $r11 + and $r11 $r10 $r11 + bra e #ih_no_other + mov $r10 0xc1c + shl b32 $r10 6 + iowr I[$r10] $r11 // INTR_UP_SET + + // ack, and wake up main() + ih_no_other: + iowr I[$r0 + 0x100] $r10 // INTR_ACK + + pop $r15 + pop $r14 + pop $r13 + pop $r11 + pop $r10 + pop $r9 + pop $r8 + mov $flags $r8 + pop $r8 + bclr $flags $p0 + iret + +// Not real sure, but, MEM_CMD 7 will hang forever if this isn't done +ctx_4160s: + mov $r14 0x4160 + sethi $r14 0x400000 + mov $r15 1 + call #nv_wr32 + ctx_4160s_wait: + call #nv_rd32 + xbit $r15 $r15 4 + bra e #ctx_4160s_wait + ret + +// Without clearing again at end of xfer, some things cause PGRAPH +// to hang with STATUS=0x00000007 until it's cleared.. fbcon can +// still function with it set however... +ctx_4160c: + mov $r14 0x4160 + sethi $r14 0x400000 + clear b32 $r15 + call #nv_wr32 + ret + +// Again, not real sure +// +// In: $r15 value to set 0x404170 to +// +ctx_4170s: + mov $r14 0x4170 + sethi $r14 0x400000 + or $r15 0x10 + call #nv_wr32 + ret + +// Waits for a ctx_4170s() call to complete +// +ctx_4170w: + mov $r14 0x4170 + sethi $r14 0x400000 + call #nv_rd32 + and $r15 0x10 + bra ne #ctx_4170w + ret + +// Disables various things, waits a bit, and re-enables them.. +// +// Not sure how exactly this helps, perhaps "ENABLE" is not such a +// good description for the bits we turn off? Anyways, without this, +// funny things happen. +// +ctx_redswitch: + mov $r14 0x614 + shl b32 $r14 6 + mov $r15 0x270 + iowr I[$r14] $r15 // HUB_RED_SWITCH = ENABLE_GPC, POWER_ALL + mov $r15 8 + ctx_redswitch_delay: + sub b32 $r15 1 + bra ne #ctx_redswitch_delay + mov $r15 0x770 + iowr I[$r14] $r15 // HUB_RED_SWITCH = ENABLE_ALL, POWER_ALL + ret + +// Not a clue what this is for, except that unless the value is 0x10, the +// strand context is saved (and presumably restored) incorrectly.. +// +// In: $r15 value to set to (0x00/0x10 are used) +// +ctx_86c: + mov $r14 0x86c + shl b32 $r14 6 + iowr I[$r14] $r15 // HUB(0x86c) = val + mov $r14 -0x75ec + sethi $r14 0x400000 + call #nv_wr32 // ROP(0xa14) = val + mov $r14 -0x5794 + sethi $r14 0x410000 + call #nv_wr32 // GPC(0x86c) = val + ret + +// ctx_load - load's a channel's ctxctl data, and selects its vm +// +// In: $r2 channel address +// +ctx_load: + trace_set(T_CHAN) + + // switch to channel, somewhat magic in parts.. + mov $r10 12 // DONE_UNK12 + call #wait_donez + mov $r1 0xa24 + shl b32 $r1 6 + iowr I[$r1 + 0x000] $r0 // 0x409a24 + mov $r3 0xb00 + shl b32 $r3 6 + iowr I[$r3 + 0x100] $r2 // CHAN_NEXT + mov $r1 0xa0c + shl b32 $r1 6 + mov $r4 7 + iowr I[$r1 + 0x000] $r2 // MEM_CHAN + iowr I[$r1 + 0x100] $r4 // MEM_CMD + ctx_chan_wait_0: + iord $r4 I[$r1 + 0x100] + and $r4 0x1f + bra ne #ctx_chan_wait_0 + iowr I[$r3 + 0x000] $r2 // CHAN_CUR + + // load channel header, fetch PGRAPH context pointer + mov $xtargets $r0 + bclr $r2 31 + shl b32 $r2 4 + add b32 $r2 2 + + trace_set(T_LCHAN) + mov $r1 0xa04 + shl b32 $r1 6 + iowr I[$r1 + 0x000] $r2 // MEM_BASE + mov $r1 0xa20 + shl b32 $r1 6 + mov $r2 0x0002 + sethi $r2 0x80000000 + iowr I[$r1 + 0x000] $r2 // MEM_TARGET = vram + mov $r1 0x10 // chan + 0x0210 + mov $r2 #xfer_data + sethi $r2 0x00020000 // 16 bytes + xdld $r1 $r2 + xdwait + trace_clr(T_LCHAN) + + // update current context + ld b32 $r1 D[$r0 + #xfer_data + 4] + shl b32 $r1 24 + ld b32 $r2 D[$r0 + #xfer_data + 0] + shr b32 $r2 8 + or $r1 $r2 + st b32 D[$r0 + #ctx_current] $r1 + + // set transfer base to start of context, and fetch context header + trace_set(T_LCTXH) + mov $r2 0xa04 + shl b32 $r2 6 + iowr I[$r2 + 0x000] $r1 // MEM_BASE + mov $r2 1 + mov $r1 0xa20 + shl b32 $r1 6 + iowr I[$r1 + 0x000] $r2 // MEM_TARGET = vm + mov $r1 #chan_data + sethi $r1 0x00060000 // 256 bytes + xdld $r0 $r1 + xdwait + trace_clr(T_LCTXH) + + trace_clr(T_CHAN) + ret + +// ctx_chan - handler for HUB_SET_CHAN command, will set a channel as +// the active channel for ctxctl, but not actually transfer +// any context data. intended for use only during initial +// context construction. +// +// In: $r2 channel address +// +ctx_chan: + call #ctx_4160s + call #ctx_load + mov $r10 12 // DONE_UNK12 + call #wait_donez + mov $r1 0xa10 + shl b32 $r1 6 + mov $r2 5 + iowr I[$r1 + 0x000] $r2 // MEM_CMD = 5 (???) + ctx_chan_wait: + iord $r2 I[$r1 + 0x000] + or $r2 $r2 + bra ne #ctx_chan_wait + call #ctx_4160c + ret + +// Execute per-context state overrides list +// +// Only executed on the first load of a channel. Might want to look into +// removing this and having the host directly modify the channel's context +// to change this state... The nouveau DRM already builds this list as +// it's definitely needed for NVIDIA's, so we may as well use it for now +// +// Input: $r1 mmio list length +// +ctx_mmio_exec: + // set transfer base to be the mmio list + ld b32 $r3 D[$r0 + #chan_mmio_address] + mov $r2 0xa04 + shl b32 $r2 6 + iowr I[$r2 + 0x000] $r3 // MEM_BASE + + clear b32 $r3 + ctx_mmio_loop: + // fetch next 256 bytes of mmio list if necessary + and $r4 $r3 0xff + bra ne #ctx_mmio_pull + mov $r5 #xfer_data + sethi $r5 0x00060000 // 256 bytes + xdld $r3 $r5 + xdwait + + // execute a single list entry + ctx_mmio_pull: + ld b32 $r14 D[$r4 + #xfer_data + 0x00] + ld b32 $r15 D[$r4 + #xfer_data + 0x04] + call #nv_wr32 + + // next! + add b32 $r3 8 + sub b32 $r1 1 + bra ne #ctx_mmio_loop + + // set transfer base back to the current context + ctx_mmio_done: + ld b32 $r3 D[$r0 + #ctx_current] + iowr I[$r2 + 0x000] $r3 // MEM_BASE + + // disable the mmio list now, we don't need/want to execute it again + st b32 D[$r0 + #chan_mmio_count] $r0 + mov $r1 #chan_data + sethi $r1 0x00060000 // 256 bytes + xdst $r0 $r1 + xdwait + ret + +// Transfer HUB context data between GPU and storage area +// +// In: $r2 channel address +// $p1 clear on save, set on load +// $p2 set if opposite direction done/will be done, so: +// on save it means: "a load will follow this save" +// on load it means: "a save preceeded this load" +// +ctx_xfer: + bra not $p1 #ctx_xfer_pre + bra $p2 #ctx_xfer_pre_load + ctx_xfer_pre: + mov $r15 0x10 + call #ctx_86c + call #ctx_4160s + bra not $p1 #ctx_xfer_exec + + ctx_xfer_pre_load: + mov $r15 2 + call #ctx_4170s + call #ctx_4170w + call #ctx_redswitch + clear b32 $r15 + call #ctx_4170s + call #ctx_load + + // fetch context pointer, and initiate xfer on all GPCs + ctx_xfer_exec: + ld b32 $r1 D[$r0 + #ctx_current] + mov $r2 0x414 + shl b32 $r2 6 + iowr I[$r2 + 0x000] $r0 // BAR_STATUS = reset + mov $r14 -0x5b00 + sethi $r14 0x410000 + mov b32 $r15 $r1 + call #nv_wr32 // GPC_BCAST_WRCMD_DATA = ctx pointer + add b32 $r14 4 + xbit $r15 $flags $p1 + xbit $r2 $flags $p2 + shl b32 $r2 1 + or $r15 $r2 + call #nv_wr32 // GPC_BCAST_WRCMD_CMD = GPC_XFER(type) + + // strands + mov $r1 0x4afc + sethi $r1 0x20000 + mov $r2 0xc + iowr I[$r1] $r2 // STRAND_CMD(0x3f) = 0x0c + call #strand_wait + mov $r2 0x47fc + sethi $r2 0x20000 + iowr I[$r2] $r0 // STRAND_FIRST_GENE(0x3f) = 0x00 + xbit $r2 $flags $p1 + add b32 $r2 3 + iowr I[$r1] $r2 // STRAND_CMD(0x3f) = 0x03/0x04 (SAVE/LOAD) + + // mmio context + xbit $r10 $flags $p1 // direction + or $r10 6 // first, last + mov $r11 0 // base = 0 + ld b32 $r12 D[$r0 + #hub_mmio_list_head] + ld b32 $r13 D[$r0 + #hub_mmio_list_tail] + mov $r14 0 // not multi + call #mmctx_xfer + + // wait for GPCs to all complete + mov $r10 8 // DONE_BAR + call #wait_doneo + + // wait for strand xfer to complete + call #strand_wait + + // post-op + bra $p1 #ctx_xfer_post + mov $r10 12 // DONE_UNK12 + call #wait_donez + mov $r1 0xa10 + shl b32 $r1 6 + mov $r2 5 + iowr I[$r1] $r2 // MEM_CMD + ctx_xfer_post_save_wait: + iord $r2 I[$r1] + or $r2 $r2 + bra ne #ctx_xfer_post_save_wait + + bra $p2 #ctx_xfer_done + ctx_xfer_post: + mov $r15 2 + call #ctx_4170s + clear b32 $r15 + call #ctx_86c + call #strand_post + call #ctx_4170w + clear b32 $r15 + call #ctx_4170s + + bra not $p1 #ctx_xfer_no_post_mmio + ld b32 $r1 D[$r0 + #chan_mmio_count] + or $r1 $r1 + bra e #ctx_xfer_no_post_mmio + call #ctx_mmio_exec + + ctx_xfer_no_post_mmio: + call #ctx_4160c + + ctx_xfer_done: + ret + +.align 256 diff --git a/driver/pscnv/nvc0_pgraph.xml.h b/driver/pscnv/nvc0_pgraph.xml.h new file mode 100644 index 00000000..62daf1a6 --- /dev/null +++ b/driver/pscnv/nvc0_pgraph.xml.h @@ -0,0 +1,2819 @@ +#ifndef ___RNNDB____RNNDB_NVC0_PGRAPH_XML +#define ___RNNDB____RNNDB_NVC0_PGRAPH_XML + +/* Autogenerated file, DO NOT EDIT manually! + +This file was generated by the rules-ng-ng headergen tool in this git repository: +http://0x04.net/cgit/index.cgi/rules-ng-ng +git clone git://0x04.net/rules-ng-ng + +The rules-ng-ng source files this header was generated from are: +- ../rnndb/../rnndb/nvc0_pgraph.xml ( 29811 bytes, from 2011-07-24 02:11:42) +- ../rnndb/copyright.xml ( 6452 bytes, from 2011-07-24 02:11:42) +- ../rnndb/nvchipsets.xml ( 3617 bytes, from 2011-07-24 02:11:42) +- ../rnndb/nv98_fuc.xml ( 8546 bytes, from 2011-10-22 19:16:00) +- ../rnndb/nv50_defs.xml ( 5468 bytes, from 2011-07-24 02:11:42) +- ../rnndb/nv50_pgraph.xml ( 48756 bytes, from 2011-09-20 22:17:16) + +Copyright (C) 2006-2011 by the following authors: +- Artur Huillet (ahuillet) +- Ben Skeggs (darktama, darktama_) +- B. R. (koala_br) +- Carlos Martin (carlosmn) +- Christoph Bumiller (calim, chrisbmr) +- Dawid Gajownik (gajownik) +- Dmitry Baryshkov +- Dmitry Eremin-Solenikov (lumag) +- EdB (edb_) +- Erik Waling (erikwaling) +- Francisco Jerez (curro) +- imirkin (imirkin) +- jb17bsome (jb17bsome) +- Jeremy Kolb (kjeremy) +- Laurent Carlier (lordheavy) +- Luca Barbieri (lb, lb1) +- Maarten Maathuis (stillunknown) +- Marcin Kościelnicki (mwk, koriakin) +- Mark Carey (careym) +- Matthieu Castet (mat-c) +- nvidiaman (nvidiaman) +- Patrice Mandin (pmandin, pmdata) +- Pekka Paalanen (pq, ppaalanen) +- Peter Popov (ironpeter) +- Richard Hughes (hughsient) +- Rudi Cilibrasi (cilibrar) +- Serge Martin +- Simon Raffeiner +- Stephane Loeuillet (leroutier) +- Stephane Marchesin (marcheu) +- sturmflut (sturmflut) +- Sylvain Munaut +- Victor Stinner (haypo) +- Wladmir van der Laan (miathan6) +- Younes Manton (ymanton) + +Permission is hereby granted, free of charge, to any person obtaining +a copy of this software and associated documentation files (the +"Software"), to deal in the Software without restriction, including +without limitation the rights to use, copy, modify, merge, publish, +distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to +the following conditions: + +The above copyright notice and this permission notice (including the +next paragraph) shall be included in all copies or substantial +portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE +LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION +OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + + +#define NVC0_PGRAPH 0x00400000 +#define NVC0_PGRAPH__ESIZE 0x00200000 + +#define NVC0_PGRAPH_INTR 0x00400100 +#define NVC0_PGRAPH_INTR_NOTIFY 0x00000001 +#define NVC0_PGRAPH_INTR_QUERY 0x00000002 +#define NVC0_PGRAPH_INTR_SYNC 0x00000004 +#define NVC0_PGRAPH_INTR_ILLEGAL_MTHD 0x00000010 +#define NVC0_PGRAPH_INTR_ILLEGAL_CLASS 0x00000020 +#define NVC0_PGRAPH_INTR_DOUBLE_NOTIFY 0x00000040 +#define NVC0_PGRAPH_INTR_UNK7 0x00000080 +#define NVC0_PGRAPH_INTR_FIRMWARE_MTHD 0x00000100 +#define NVC0_PGRAPH_INTR_BUFFER_NOTIFY 0x00010000 +#define NVC0_PGRAPH_INTR_CTXCTL_UP 0x00080000 +#define NVC0_PGRAPH_INTR_DATA_ERROR 0x00100000 +#define NVC0_PGRAPH_INTR_TRAP 0x00200000 +#define NVC0_PGRAPH_INTR_SINGLE_STEP 0x01000000 + +#define NVC0_PGRAPH_TRAP 0x00400108 +#define NVC0_PGRAPH_TRAP_DISPATCH 0x00000001 +#define NVC0_PGRAPH_TRAP_M2MF 0x00000002 +#define NVC0_PGRAPH_TRAP_UNK2 0x00000004 +#define NVC0_PGRAPH_TRAP_CCACHE 0x00000008 +#define NVC0_PGRAPH_TRAP_UNK4 0x00000010 +#define NVC0_PGRAPH_TRAP_UNK5 0x00000020 +#define NVC0_PGRAPH_TRAP_UNK6 0x00000040 +#define NVC0_PGRAPH_TRAP_MACRO 0x00000080 +#define NVC0_PGRAPH_TRAP_GPC 0x01000000 +#define NVC0_PGRAPH_TRAP_ROPC 0x02000000 + +#define NVC0_PGRAPH_DATA_ERROR 0x00400110 + +#define NVC0_PGRAPH_TRAP_GPCS 0x00400118 + +#define NVC0_PGRAPH_TRAP_ROPCS 0x0040011c + +#define NVC0_PGRAPH_INTR_UNK1 0x00400120 +#define NVC0_PGRAPH_INTR_UNK1_QUERY 0x00000002 + +#define NVC0_PGRAPH_INTR_EN_UNK1 0x00400124 +#define NVC0_PGRAPH_INTR_EN_UNK1_QUERY 0x00000002 + +#define NVC0_PGRAPH_TRAP_GPCS_EN 0x00400130 + +#define NVC0_PGRAPH_TRAP_ROPCS_EN 0x00400134 + +#define NVC0_PGRAPH_TRAP_EN 0x00400138 +#define NVC0_PGRAPH_TRAP_EN_DISPATCH 0x00000001 +#define NVC0_PGRAPH_TRAP_EN_M2MF 0x00000002 +#define NVC0_PGRAPH_TRAP_EN_UNK2 0x00000004 +#define NVC0_PGRAPH_TRAP_EN_CCACHE 0x00000008 +#define NVC0_PGRAPH_TRAP_EN_UNK4 0x00000010 +#define NVC0_PGRAPH_TRAP_EN_UNK5 0x00000020 +#define NVC0_PGRAPH_TRAP_EN_UNK6 0x00000040 +#define NVC0_PGRAPH_TRAP_EN_MACRO 0x00000080 +#define NVC0_PGRAPH_TRAP_EN_GPC 0x01000000 +#define NVC0_PGRAPH_TRAP_EN_ROPC 0x02000000 + +#define NVC0_PGRAPH_INTR_EN 0x0040013c +#define NVC0_PGRAPH_INTR_EN_NOTIFY 0x00000001 +#define NVC0_PGRAPH_INTR_EN_QUERY 0x00000002 +#define NVC0_PGRAPH_INTR_EN_SYNC 0x00000004 +#define NVC0_PGRAPH_INTR_EN_ILLEGAL_MTHD 0x00000010 +#define NVC0_PGRAPH_INTR_EN_ILLEGAL_CLASS 0x00000020 +#define NVC0_PGRAPH_INTR_EN_DOUBLE_NOTIFY 0x00000040 +#define NVC0_PGRAPH_INTR_EN_UNK7 0x00000080 +#define NVC0_PGRAPH_INTR_EN_FIRMWARE_MTHD 0x00000100 +#define NVC0_PGRAPH_INTR_EN_BUFFER_NOTIFY 0x00010000 +#define NVC0_PGRAPH_INTR_EN_CTXCTL_UP 0x00080000 +#define NVC0_PGRAPH_INTR_EN_DATA_ERROR 0x00100000 +#define NVC0_PGRAPH_INTR_EN_TRAP 0x00200000 +#define NVC0_PGRAPH_INTR_EN_SINGLE_STEP 0x01000000 + +#define NVC0_PGRAPH_INTR_DISPATCH_CTXCTL_DOWN 0x00400140 +#define NVC0_PGRAPH_INTR_DISPATCH_CTXCTL_DOWN_ILLEGAL_MTHD 0x00000010 +#define NVC0_PGRAPH_INTR_DISPATCH_CTXCTL_DOWN_FIRMWARE_MTHD 0x00000100 + +#define NVC0_PGRAPH_INTR_CTXCTL_DOWN 0x00400144 +#define NVC0_PGRAPH_INTR_CTXCTL_DOWN_ILLEGAL_MTHD 0x00000010 +#define NVC0_PGRAPH_INTR_CTXCTL_DOWN_FIRMWARE_MTHD 0x00000100 + +#define NVC0_PGRAPH_INTR_EN_CTXCTL_DOWN 0x00400148 +#define NVC0_PGRAPH_INTR_EN_CTXCTL_DOWN_ILLEGAL_MTHD 0x00000010 +#define NVC0_PGRAPH_INTR_EN_CTXCTL_DOWN_FIRMWARE_MTHD 0x00000100 + +#define NVC0_PGRAPH_ICMD_CMD 0x00400200 + +#define NVC0_PGRAPH_ICMD_DATA 0x00400204 + +#define NVC0_PGRAPH_FIFO 0x00400500 + +#define NVC0_PGRAPH_FIFO_CONTROL 0x00400500 +#define NVC0_PGRAPH_FIFO_CONTROL_PULL 0x00000001 +#define NVC0_PGRAPH_FIFO_CONTROL_UNK8 0x00000100 +#define NVC0_PGRAPH_FIFO_CONTROL_UNK16 0x00010000 +#define NVC0_PGRAPH_FIFO_CONTROL_LIMIT__MASK 0x1ff00000 +#define NVC0_PGRAPH_FIFO_CONTROL_LIMIT__SHIFT 20 + +#define NVC0_PGRAPH_FIFO_STATUS 0x00400504 +#define NVC0_PGRAPH_FIFO_STATUS_EMPTY 0x00000001 +#define NVC0_PGRAPH_FIFO_STATUS_FULL 0x00000002 +#define NVC0_PGRAPH_FIFO_STATUS_OCCUPIED__MASK 0x0000fff0 +#define NVC0_PGRAPH_FIFO_STATUS_OCCUPIED__SHIFT 4 +#define NVC0_PGRAPH_FIFO_STATUS_GET__MASK 0x00ff0000 +#define NVC0_PGRAPH_FIFO_STATUS_GET__SHIFT 16 +#define NVC0_PGRAPH_FIFO_STATUS_PUT__MASK 0xff000000 +#define NVC0_PGRAPH_FIFO_STATUS_PUT__SHIFT 24 + +#define NVC0_PGRAPH_STATUS 0x00400700 +#define NVC0_PGRAPH_STATUS_ALL 0x00000001 +#define NVC0_PGRAPH_STATUS_M2MF 0x00000040 +#define NVC0_PGRAPH_STATUS_CTXCTL 0x00000080 +#define NVC0_PGRAPH_STATUS_GPC 0x01000000 +#define NVC0_PGRAPH_STATUS_ROPC 0x02000000 + +#define NVC0_PGRAPH_TRAPPED_ADDR 0x00400704 +#define NVC0_PGRAPH_TRAPPED_ADDR_MTHD__MASK 0x00003ffc +#define NVC0_PGRAPH_TRAPPED_ADDR_MTHD__SHIFT 2 +#define NVC0_PGRAPH_TRAPPED_ADDR_MTHD__SHR 2 +#define NVC0_PGRAPH_TRAPPED_ADDR_SUBCH__MASK 0x00070000 +#define NVC0_PGRAPH_TRAPPED_ADDR_SUBCH__SHIFT 16 + +#define NVC0_PGRAPH_TRAPPED_DATA_LOW 0x00400708 + +#define NVC0_PGRAPH_TRAPPED_DATA_HIGH 0x0040070c + +#define NVC0_PGRAPH_DISPATCH 0x00404000 +#define NVC0_PGRAPH_DISPATCH__ESIZE 0x00000400 + +#define NVC0_PGRAPH_DISPATCH_TRAP 0x00404000 +#define NVC0_PGRAPH_DISPATCH_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_DISPATCH_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR 0x00404004 +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_MTHD__MASK 0x00001ffc +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_MTHD__SHIFT 2 +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_MTHD__SHR 2 +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_SUBCH__MASK 0x00070000 +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_SUBCH__SHIFT 16 +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_NONINCR 0x00100000 +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_UNK1 0x00200000 +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_SINGLE_STEP_DONE 0x00400000 +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_DOUBLE 0x02000000 +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_CURRENT_SUBCH 0x20000000 +#define NVC0_PGRAPH_DISPATCH_CMD_ADDR_VALID 0x80000000 + +#define NVC0_PGRAPH_DISPATCH_CMD_DATA_LOW 0x00404008 + +#define NVC0_PGRAPH_DISPATCH_CMD_DATA_HIGH 0x0040400c + +#define NVC0_PGRAPH_DISPATCH_CTX_SWITCH 0x00404010 + +#define NVC0_PGRAPH_DISPATCH_SUBCH 0x00404024 +#define NVC0_PGRAPH_DISPATCH_SUBCH_SUBCH__MASK 0x0000e000 +#define NVC0_PGRAPH_DISPATCH_SUBCH_SUBCH__SHIFT 13 + +#define NVC0_PGRAPH_DISPATCH_MISC 0x00404028 +#define NVC0_PGRAPH_DISPATCH_MISC_NOTIFY_PENDING 0x00000100 +#define NVC0_PGRAPH_DISPATCH_MISC_NOTIFY_AWAKEN 0x00010000 + +#define NVC0_PGRAPH_DISPATCH_ST2_ADDR 0x0040402c +#define NVC0_PGRAPH_DISPATCH_ST2_ADDR_MTHD__MASK 0x00001ffc +#define NVC0_PGRAPH_DISPATCH_ST2_ADDR_MTHD__SHIFT 2 +#define NVC0_PGRAPH_DISPATCH_ST2_ADDR_MTHD__SHR 2 +#define NVC0_PGRAPH_DISPATCH_ST2_ADDR_ILLEGAL_CLASS 0x20000000 +#define NVC0_PGRAPH_DISPATCH_ST2_ADDR_ILLEGAL_MTHD 0x40000000 +#define NVC0_PGRAPH_DISPATCH_ST2_ADDR_VALID 0x80000000 + +#define NVC0_PGRAPH_DISPATCH_ST2_DATA_LOW 0x0040403c + +#define NVC0_PGRAPH_DISPATCH_ST2_DATA_HIGH 0x00404040 + +#define NVC0_PGRAPH_DISPATCH_ST3_ADDR 0x00404048 +#define NVC0_PGRAPH_DISPATCH_ST3_ADDR_MTHD__MASK 0x00001ffc +#define NVC0_PGRAPH_DISPATCH_ST3_ADDR_MTHD__SHIFT 2 +#define NVC0_PGRAPH_DISPATCH_ST3_ADDR_MTHD__SHR 2 +#define NVC0_PGRAPH_DISPATCH_ST3_ADDR_VALID 0x80000000 + +#define NVC0_PGRAPH_DISPATCH_ST3_DATA_LOW 0x00404050 + +#define NVC0_PGRAPH_DISPATCH_ST3_DATA_HIGH 0x00404054 + +#define NVC0_PGRAPH_DISPATCH_COND_ADDRESS_HIGH 0x004040c0 + +#define NVC0_PGRAPH_DISPATCH_COND_ADDRESS_LOW 0x004040c4 + +#define NVC0_PGRAPH_DISPATCH_NOTIFY_3D_ADDRESS_HIGH 0x004040d0 + +#define NVC0_PGRAPH_DISPATCH_NOTIFY_3D_ADDRESS_LOW 0x004040d4 + +#define NVC0_PGRAPH_DISPATCH_NOTIFY_2D_ADDRESS_HIGH 0x004040d8 + +#define NVC0_PGRAPH_DISPATCH_NOTIFY_2D_ADDRESS_LOW 0x004040dc + +#define NVC0_PGRAPH_DISPATCH_NOTIFY_M2MF_ADDRESS_HIGH 0x004040e0 + +#define NVC0_PGRAPH_DISPATCH_NOTIFY_M2MF_ADDRESS_LOW 0x004040e4 + +#define NVC0_PGRAPH_DISPATCH_CTX_CACHE(i0) (0x00404200 + 0x4*(i0)) +#define NVC0_PGRAPH_DISPATCH_CTX_CACHE__ESIZE 0x00000004 +#define NVC0_PGRAPH_DISPATCH_CTX_CACHE__LEN 0x00000008 + +#define NVC0_PGRAPH_MACRO 0x00404400 +#define NVC0_PGRAPH_MACRO__ESIZE 0x00000100 + +#define NVC0_PGRAPH_MACRO_REG(i0) (0x00404400 + 0x4*(i0)) +#define NVC0_PGRAPH_MACRO_REG__ESIZE 0x00000004 +#define NVC0_PGRAPH_MACRO_REG__LEN 0x00000008 + +#define NVC0_PGRAPH_MACRO_MCACHE_CTRL 0x00404488 +#define NVC0_PGRAPH_MACRO_MCACHE_CTRL_CLASS__MASK 0x0000ffff +#define NVC0_PGRAPH_MACRO_MCACHE_CTRL_CLASS__SHIFT 0 +#define NVC0_PGRAPH_MACRO_MCACHE_CTRL_MTHD__MASK 0x0fff0000 +#define NVC0_PGRAPH_MACRO_MCACHE_CTRL_MTHD__SHIFT 16 +#define NVC0_PGRAPH_MACRO_MCACHE_CTRL_MTHD__SHR 2 +#define NVC0_PGRAPH_MACRO_MCACHE_CTRL_READ_TRIGGER 0x40000000 +#define NVC0_PGRAPH_MACRO_MCACHE_CTRL_WRITE_TRIGGER 0x80000000 + +#define NVC0_PGRAPH_MACRO_MCACHE_DATA 0x0040448c + +#define NVC0_PGRAPH_MACRO_TRAP 0x00404490 +#define NVC0_PGRAPH_MACRO_TRAP_TOO_FEW_PARAMS 0x00000001 +#define NVC0_PGRAPH_MACRO_TRAP_TOO_MANY_PARAMS 0x00000002 +#define NVC0_PGRAPH_MACRO_TRAP_ILLEGAL_OPCODE 0x00000004 +#define NVC0_PGRAPH_MACRO_TRAP_DOUBLE_BRANCH 0x00000008 +#define NVC0_PGRAPH_MACRO_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_MACRO_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_M2MF 0x00404600 +#define NVC0_PGRAPH_M2MF__ESIZE 0x00000200 + +#define NVC0_PGRAPH_M2MF_TRAP 0x00404600 +#define NVC0_PGRAPH_M2MF_TRAP_PUSH_TOO_MUCH_DATA 0x00000001 +#define NVC0_PGRAPH_M2MF_TRAP_PUSH_NOT_ENOUGH_DATA 0x00000002 +#define NVC0_PGRAPH_M2MF_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_M2MF_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_DDATA 0x00404800 +#define NVC0_PGRAPH_DDATA__ESIZE 0x00000800 + +#define NVC0_PGRAPH_UNK5800 0x00405800 +#define NVC0_PGRAPH_UNK5800__ESIZE 0x00000800 + +#define NVC0_PGRAPH_UNK5800_TRAP 0x00405840 +#define NVC0_PGRAPH_UNK5800_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_UNK5800_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_UNK5800_TRAP_UNK44 0x00405844 + +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT(i0) (0x00405870 + 0x4*(i0)) +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT__ESIZE 0x00000004 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT__LEN 0x00000004 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_0__MASK 0x0000000f +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_0__SHIFT 0 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_1__MASK 0x000000f0 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_1__SHIFT 4 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_2__MASK 0x00000f00 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_2__SHIFT 8 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_3__MASK 0x0000f000 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_3__SHIFT 12 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_4__MASK 0x000f0000 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_4__SHIFT 16 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_5__MASK 0x00f00000 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_5__SHIFT 20 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_6__MASK 0x0f000000 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_6__SHIFT 24 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_7__MASK 0xf0000000 +#define NVC0_PGRAPH_UNK5800_GPC_TPCNT_7__SHIFT 28 + +#define NVC0_PGRAPH_UNK6000 0x00406000 +#define NVC0_PGRAPH_UNK6000__ESIZE 0x00000800 + +#define NVC0_PGRAPH_UNK6000_TRAP_UNK0 0x00406018 +#define NVC0_PGRAPH_UNK6000_TRAP_UNK0_CLEAR 0x40000000 +#define NVC0_PGRAPH_UNK6000_TRAP_UNK0_ENABLE 0x80000000 + +#define NVC0_PGRAPH_UNK6000_TRAP_UNK1 0x0040601c +#define NVC0_PGRAPH_UNK6000_TRAP_UNK1_TEMP_TOO_SMALL 0x00000001 +#define NVC0_PGRAPH_UNK6000_TRAP_UNK1_CLEAR 0x40000000 +#define NVC0_PGRAPH_UNK6000_TRAP_UNK1_ENABLE 0x80000000 + +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT(i0) (0x00406028 + 0x4*(i0)) +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT__ESIZE 0x00000004 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT__LEN 0x00000004 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_0__MASK 0x0000000f +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_0__SHIFT 0 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_1__MASK 0x000000f0 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_1__SHIFT 4 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_2__MASK 0x00000f00 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_2__SHIFT 8 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_3__MASK 0x0000f000 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_3__SHIFT 12 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_4__MASK 0x000f0000 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_4__SHIFT 16 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_5__MASK 0x00f00000 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_5__SHIFT 20 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_6__MASK 0x0f000000 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_6__SHIFT 24 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_7__MASK 0xf0000000 +#define NVC0_PGRAPH_UNK6000_GPC_TPCNT_7__SHIFT 28 + +#define NVC0_PGRAPH_UNK6000_TP_GPCID(i0) (0x004060a8 + 0x4*(i0)) +#define NVC0_PGRAPH_UNK6000_TP_GPCID__ESIZE 0x00000004 +#define NVC0_PGRAPH_UNK6000_TP_GPCID__LEN 0x00000040 +#define NVC0_PGRAPH_UNK6000_TP_GPCID_0__MASK 0x0000001f +#define NVC0_PGRAPH_UNK6000_TP_GPCID_0__SHIFT 0 +#define NVC0_PGRAPH_UNK6000_TP_GPCID_1__MASK 0x00001f00 +#define NVC0_PGRAPH_UNK6000_TP_GPCID_1__SHIFT 8 +#define NVC0_PGRAPH_UNK6000_TP_GPCID_2__MASK 0x001f0000 +#define NVC0_PGRAPH_UNK6000_TP_GPCID_2__SHIFT 16 +#define NVC0_PGRAPH_UNK6000_TP_GPCID_3__MASK 0x1f000000 +#define NVC0_PGRAPH_UNK6000_TP_GPCID_3__SHIFT 24 + +#define NVC0_PGRAPH_UNK6000_TEMP_SIZE_PER_MP 0x004064b0 +#define NVC0_PGRAPH_UNK6000_TEMP_SIZE_PER_MP__SHR 8 + + +#define NVC0_PGRAPH_TPGRAD(i0, i1) (0x00406800 + 0x400*(i0) + 0x20*(i1)) +#define NVC0_PGRAPH_TPGRAD__ESIZE 0x00000020 +#define NVC0_PGRAPH_TPGRAD__LEN 0x00000020 + +#define NVC0_PGRAPH_TPGRAD_MASK(i0, i1, i2) (0x00406800 + 0x400*(i0) + 0x20*(i1) + 0x4*(i2)) +#define NVC0_PGRAPH_TPGRAD_MASK__ESIZE 0x00000004 +#define NVC0_PGRAPH_TPGRAD_MASK__LEN 0x00000008 + +#define NVC0_PGRAPH_TPBUS 0x00407800 +#define NVC0_PGRAPH_TPBUS__ESIZE 0x00000800 + +#define NVC0_PGRAPH_TPBUS_TP_GPCID(i0) (0x0040780c + 0x4*(i0)) +#define NVC0_PGRAPH_TPBUS_TP_GPCID__ESIZE 0x00000004 +#define NVC0_PGRAPH_TPBUS_TP_GPCID__LEN 0x0000002c +#define NVC0_PGRAPH_TPBUS_TP_GPCID_0__MASK 0x0000001f +#define NVC0_PGRAPH_TPBUS_TP_GPCID_0__SHIFT 0 +#define NVC0_PGRAPH_TPBUS_TP_GPCID_1__MASK 0x000003e0 +#define NVC0_PGRAPH_TPBUS_TP_GPCID_1__SHIFT 5 +#define NVC0_PGRAPH_TPBUS_TP_GPCID_2__MASK 0x00007c00 +#define NVC0_PGRAPH_TPBUS_TP_GPCID_2__SHIFT 10 +#define NVC0_PGRAPH_TPBUS_TP_GPCID_3__MASK 0x000f8000 +#define NVC0_PGRAPH_TPBUS_TP_GPCID_3__SHIFT 15 +#define NVC0_PGRAPH_TPBUS_TP_GPCID_4__MASK 0x01f00000 +#define NVC0_PGRAPH_TPBUS_TP_GPCID_4__SHIFT 20 +#define NVC0_PGRAPH_TPBUS_TP_GPCID_5__MASK 0x3e000000 +#define NVC0_PGRAPH_TPBUS_TP_GPCID_5__SHIFT 25 + +#define NVC0_PGRAPH_TPBUS_TOTAL 0x004078bc +#define NVC0_PGRAPH_TPBUS_TOTAL_ROPC_COUNT__MASK 0x000000ff +#define NVC0_PGRAPH_TPBUS_TOTAL_ROPC_COUNT__SHIFT 0 +#define NVC0_PGRAPH_TPBUS_TOTAL_GPC_COUNT__MASK 0x0000ff00 +#define NVC0_PGRAPH_TPBUS_TOTAL_GPC_COUNT__SHIFT 8 + +#define NVC0_PGRAPH_CCACHE 0x00408000 +#define NVC0_PGRAPH_CCACHE__ESIZE 0x00000800 + +#define NVC0_PGRAPH_CCACHE_HUB2GPC_ADDR 0x00408004 +#define NVC0_PGRAPH_CCACHE_HUB2GPC_ADDR__SHR 8 + +#define NVC0_PGRAPH_CCACHE_HUB2GPC_CONF 0x00408008 +#define NVC0_PGRAPH_CCACHE_HUB2GPC_CONF_UNK0__MASK 0x000000ff +#define NVC0_PGRAPH_CCACHE_HUB2GPC_CONF_UNK0__SHIFT 0 +#define NVC0_PGRAPH_CCACHE_HUB2GPC_CONF_UNK8__MASK 0x00000700 +#define NVC0_PGRAPH_CCACHE_HUB2GPC_CONF_UNK8__SHIFT 8 +#define NVC0_PGRAPH_CCACHE_HUB2GPC_CONF_UNK31 0x80000000 + +#define NVC0_PGRAPH_CCACHE_HUB2ESETUP_ADDR 0x0040800c +#define NVC0_PGRAPH_CCACHE_HUB2ESETUP_ADDR__SHR 8 + +#define NVC0_PGRAPH_CCACHE_HUB2ESETUP_CONF 0x00408010 +#define NVC0_PGRAPH_CCACHE_HUB2ESETUP_CONF_UNK0__MASK 0x000007ff +#define NVC0_PGRAPH_CCACHE_HUB2ESETUP_CONF_UNK0__SHIFT 0 +#define NVC0_PGRAPH_CCACHE_HUB2ESETUP_CONF_UNK11__MASK 0x0000f800 +#define NVC0_PGRAPH_CCACHE_HUB2ESETUP_CONF_UNK11__SHIFT 11 +#define NVC0_PGRAPH_CCACHE_HUB2ESETUP_CONF_UNK31 0x80000000 + +#define NVC0_PGRAPH_CCACHE_TRAP 0x00408030 +#define NVC0_PGRAPH_CCACHE_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_CCACHE_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_CTXCTL 0x00409000 +#define NVC0_PGRAPH_CTXCTL__ESIZE 0x00001000 + + + +#define NVC0_PGRAPH_CTXCTL_INTR_TRIGGER 0x00409000 +#define NVC0_PGRAPH_CTXCTL_INTR_TRIGGER_PERIODIC 0x00000001 +#define NVC0_PGRAPH_CTXCTL_INTR_TRIGGER_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_CTXCTL_INTR_TRIGGER_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_CTXCTL_INTR_TRIGGER_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_CTXCTL_INTR_TRIGGER_EXIT 0x00000010 +#define NVC0_PGRAPH_CTXCTL_INTR_TRIGGER_USER1 0x00000040 +#define NVC0_PGRAPH_CTXCTL_INTR_TRIGGER_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_CTXCTL_INTR_ACK 0x00409004 +#define NVC0_PGRAPH_CTXCTL_INTR_ACK_PERIODIC 0x00000001 +#define NVC0_PGRAPH_CTXCTL_INTR_ACK_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_CTXCTL_INTR_ACK_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_CTXCTL_INTR_ACK_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_CTXCTL_INTR_ACK_EXIT 0x00000010 +#define NVC0_PGRAPH_CTXCTL_INTR_ACK_USER1 0x00000040 +#define NVC0_PGRAPH_CTXCTL_INTR_ACK_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_CTXCTL_INTR 0x00409008 +#define NVC0_PGRAPH_CTXCTL_INTR_PERIODIC 0x00000001 +#define NVC0_PGRAPH_CTXCTL_INTR_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_CTXCTL_INTR_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_CTXCTL_INTR_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_CTXCTL_INTR_EXIT 0x00000010 +#define NVC0_PGRAPH_CTXCTL_INTR_USER1 0x00000040 +#define NVC0_PGRAPH_CTXCTL_INTR_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_CTXCTL_INTR_EN_SET 0x00409010 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_SET_PERIODIC 0x00000001 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_SET_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_SET_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_SET_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_SET_EXIT 0x00000010 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_SET_USER1 0x00000040 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_SET_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_CTXCTL_INTR_EN_CLR 0x00409014 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_CLR_PERIODIC 0x00000001 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_CLR_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_CLR_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_CLR_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_CLR_EXIT 0x00000010 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_CLR_USER1 0x00000040 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_CLR_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_CTXCTL_INTR_EN 0x00409018 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_PERIODIC 0x00000001 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_EXIT 0x00000010 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_USER1 0x00000040 +#define NVC0_PGRAPH_CTXCTL_INTR_EN_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING 0x0040901c +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M1__MASK 0x0000ffff +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M1__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M1_PERIODIC 0x00000001 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M1_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M1_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M1_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M1_EXIT 0x00000010 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M1_USER1 0x00000040 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M1_XFER_FAULT 0x00000200 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M2__MASK 0xffff0000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M2__SHIFT 16 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M2_PERIODIC 0x00010000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M2_WATCHDOG 0x00020000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M2_FIFO_DATA 0x00040000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M2_CHANNEL_SWITCH 0x00080000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M2_EXIT 0x00100000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M2_USER1 0x00400000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTING_M2_XFER_FAULT 0x02000000 + +#define NVC0_PGRAPH_CTXCTL_PERIODIC_PERIOD 0x00409020 + +#define NVC0_PGRAPH_CTXCTL_PERIODIC_TIME 0x00409024 + +#define NVC0_PGRAPH_CTXCTL_PERIODIC_ENABLE 0x00409028 + +#define NVC0_PGRAPH_CTXCTL_TIME_LOW 0x0040902c + +#define NVC0_PGRAPH_CTXCTL_TIME_HIGH 0x00409030 + +#define NVC0_PGRAPH_CTXCTL_WATCHDOG_TIME 0x00409034 + +#define NVC0_PGRAPH_CTXCTL_WATCHDOG_ENABLE 0x00409038 + +#define NVC0_PGRAPH_CTXCTL_SCRATCH(i0) (0x00409040 + 0x4*(i0)) +#define NVC0_PGRAPH_CTXCTL_SCRATCH__ESIZE 0x00000004 +#define NVC0_PGRAPH_CTXCTL_SCRATCH__LEN 0x00000002 + +#define NVC0_PGRAPH_CTXCTL_ACCESS_EN 0x00409048 +#define NVC0_PGRAPH_CTXCTL_ACCESS_EN_CHANNEL_SWITCH 0x00000001 +#define NVC0_PGRAPH_CTXCTL_ACCESS_EN_FIFO 0x00000002 + +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR 0x00409050 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_CHAN__MASK 0x3fffffff +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_CHAN__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_CHAN_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_CHAN_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_CHAN_ADDRESS__SHR 12 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_CHAN_TARGET__MASK 0x30000000 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_CHAN_TARGET__SHIFT 28 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_CHAN_TARGET_VRAM 0x00000000 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_CHAN_TARGET_SYSRAM 0x20000000 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_CHAN_TARGET_SYSRAM_NO_SNOOP 0x30000000 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_CUR_VALID 0x40000000 + +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT 0x00409054 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_CHAN__MASK 0x3fffffff +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_CHAN__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_CHAN_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_CHAN_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_CHAN_ADDRESS__SHR 12 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_CHAN_TARGET__MASK 0x30000000 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_CHAN_TARGET__SHIFT 28 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_CHAN_TARGET_VRAM 0x00000000 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_CHAN_TARGET_SYSRAM 0x20000000 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_CHAN_TARGET_SYSRAM_NO_SNOOP 0x30000000 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_NEXT_VALID 0x40000000 + +#define NVC0_PGRAPH_CTXCTL_CHANNEL_TRIGGER 0x00409054 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_TRIGGER_UNLOAD 0x00000001 +#define NVC0_PGRAPH_CTXCTL_CHANNEL_TRIGGER_LOAD 0x00000002 + +#define NVC0_PGRAPH_CTXCTL_FIFO_DATA 0x00409064 + +#define NVC0_PGRAPH_CTXCTL_FIFO_CMD 0x00409068 +#define NVC0_PGRAPH_CTXCTL_FIFO_CMD_MTHD__MASK 0x000007ff +#define NVC0_PGRAPH_CTXCTL_FIFO_CMD_MTHD__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_FIFO_CMD_MTHD__SHR 2 +#define NVC0_PGRAPH_CTXCTL_FIFO_CMD_SUBC__MASK 0x00003800 +#define NVC0_PGRAPH_CTXCTL_FIFO_CMD_SUBC__SHIFT 11 +#define NVC0_PGRAPH_CTXCTL_FIFO_CMD_NONINCR 0x00004000 + +#define NVC0_PGRAPH_CTXCTL_FIFO_OCCUPIED 0x00409070 + +#define NVC0_PGRAPH_CTXCTL_FIFO_ACK 0x00409074 + +#define NVC0_PGRAPH_CTXCTL_FIFO_LIMIT 0x00409078 + +#define NVC0_PGRAPH_CTXCTL_MISC_TRIGGER 0x00409088 +#define NVC0_PGRAPH_CTXCTL_MISC_TRIGGER_WRCACHE_FLUSH 0x00010000 +#define NVC0_PGRAPH_CTXCTL_MISC_TRIGGER_PM_TRIGGER 0x00020000 + +#define NVC0_PGRAPH_CTXCTL_UC_CTRL 0x00409100 +#define NVC0_PGRAPH_CTXCTL_UC_CTRL_START_TRIGGER 0x00000002 +#define NVC0_PGRAPH_CTXCTL_UC_CTRL_RESET_UNK2_TRIGGER 0x00000004 +#define NVC0_PGRAPH_CTXCTL_UC_CTRL_RESET_UNK3_TRIGGER 0x00000008 +#define NVC0_PGRAPH_CTXCTL_UC_CTRL_STOPPED 0x00000010 +#define NVC0_PGRAPH_CTXCTL_UC_CTRL_SLEEPING 0x00000020 + +#define NVC0_PGRAPH_CTXCTL_ENTRY 0x00409104 + +#define NVC0_PGRAPH_CTXCTL_CAPS 0x00409108 +#define NVC0_PGRAPH_CTXCTL_CAPS_CODE_SIZE__MASK 0x000001ff +#define NVC0_PGRAPH_CTXCTL_CAPS_CODE_SIZE__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_CAPS_CODE_SIZE__SHR 8 +#define NVC0_PGRAPH_CTXCTL_CAPS_DATA_SIZE__MASK 0x0001fe00 +#define NVC0_PGRAPH_CTXCTL_CAPS_DATA_SIZE__SHIFT 9 +#define NVC0_PGRAPH_CTXCTL_CAPS_DATA_SIZE__SHR 8 + +#define NVC0_PGRAPH_CTXCTL_XFER_EXT_BASE 0x00409110 +#define NVC0_PGRAPH_CTXCTL_XFER_EXT_BASE__SHR 8 + +#define NVC0_PGRAPH_CTXCTL_XFER_FUC_ADDR 0x00409114 + +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL 0x00409118 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_FULL 0x00000001 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SEG__MASK 0x00000010 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SEG__SHIFT 4 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SEG_DATA 0x00000000 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SEG_CODE 0x00000010 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_DIR__MASK 0x00000020 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_DIR__SHIFT 5 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_DIR_LOAD 0x00000000 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_DIR_STORE 0x00000020 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SIZE__MASK 0x00000700 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SIZE__SHIFT 8 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SIZE_16 0x00000200 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SIZE_32 0x00000300 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SIZE_64 0x00000400 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SIZE_128 0x00000500 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_SIZE_256 0x00000600 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_TARGET__MASK 0x00007000 +#define NVC0_PGRAPH_CTXCTL_XFER_CTRL_TARGET__SHIFT 12 + +#define NVC0_PGRAPH_CTXCTL_XFER_EXT_ADDR 0x0040911c + +#define NVC0_PGRAPH_CTXCTL_XFER_STATUS 0x00409120 +#define NVC0_PGRAPH_CTXCTL_XFER_STATUS_PENDING 0x00000002 +#define NVC0_PGRAPH_CTXCTL_XFER_STATUS_UNK4__MASK 0x00000030 +#define NVC0_PGRAPH_CTXCTL_XFER_STATUS_UNK4__SHIFT 4 +#define NVC0_PGRAPH_CTXCTL_XFER_STATUS_STORES_PENDING__MASK 0x00070000 +#define NVC0_PGRAPH_CTXCTL_XFER_STATUS_STORES_PENDING__SHIFT 16 +#define NVC0_PGRAPH_CTXCTL_XFER_STATUS_LOADS_PENDING__MASK 0x07000000 +#define NVC0_PGRAPH_CTXCTL_XFER_STATUS_LOADS_PENDING__SHIFT 24 + +#define NVC0_PGRAPH_CTXCTL_UC_STATUS 0x00409128 +#define NVC0_PGRAPH_CTXCTL_UC_STATUS_XCLD_IDLE 0x00000004 +#define NVC0_PGRAPH_CTXCTL_UC_STATUS_CRYPT_IDLE 0x00000008 +#define NVC0_PGRAPH_CTXCTL_UC_STATUS_TRAP_ACTIVE 0x00000100 +#define NVC0_PGRAPH_CTXCTL_UC_STATUS_XDST_IDLE 0x00040000 +#define NVC0_PGRAPH_CTXCTL_UC_STATUS_XDLD_IDLE 0x00080000 + +#define NVC0_PGRAPH_CTXCTL_CAPS2 0x0040912c +#define NVC0_PGRAPH_CTXCTL_CAPS2_UNK0__MASK 0x0000000f +#define NVC0_PGRAPH_CTXCTL_CAPS2_UNK0__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_CAPS2_SECRETFUL__MASK 0x000000f0 +#define NVC0_PGRAPH_CTXCTL_CAPS2_SECRETFUL__SHIFT 4 +#define NVC0_PGRAPH_CTXCTL_CAPS2_CODE_PORTS__MASK 0x00000f00 +#define NVC0_PGRAPH_CTXCTL_CAPS2_CODE_PORTS__SHIFT 8 +#define NVC0_PGRAPH_CTXCTL_CAPS2_DATA_PORTS__MASK 0x0000f000 +#define NVC0_PGRAPH_CTXCTL_CAPS2_DATA_PORTS__SHIFT 12 +#define NVC0_PGRAPH_CTXCTL_CAPS2_VM_PAGES_LOG2__MASK 0x000f0000 +#define NVC0_PGRAPH_CTXCTL_CAPS2_VM_PAGES_LOG2__SHIFT 16 + +#define NVC0_PGRAPH_CTXCTL_TLB_CMD 0x00409140 +#define NVC0_PGRAPH_CTXCTL_TLB_CMD_PARAM__MASK 0x00ffffff +#define NVC0_PGRAPH_CTXCTL_TLB_CMD_PARAM__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_TLB_CMD_CMD__MASK 0x03000000 +#define NVC0_PGRAPH_CTXCTL_TLB_CMD_CMD__SHIFT 24 +#define NVC0_PGRAPH_CTXCTL_TLB_CMD_CMD_ITLB 0x01000000 +#define NVC0_PGRAPH_CTXCTL_TLB_CMD_CMD_PTLB 0x02000000 +#define NVC0_PGRAPH_CTXCTL_TLB_CMD_CMD_VTLB 0x03000000 + +#define NVC0_PGRAPH_CTXCTL_TLB_CMD_RES 0x00409144 + +#define NVC0_PGRAPH_CTXCTL_CODE_INDEX 0x00409180 +#define NVC0_PGRAPH_CTXCTL_CODE_INDEX_PHYS_ADDR__MASK 0x0000fffc +#define NVC0_PGRAPH_CTXCTL_CODE_INDEX_PHYS_ADDR__SHIFT 2 +#define NVC0_PGRAPH_CTXCTL_CODE_INDEX_PHYS_ADDR__SHR 2 +#define NVC0_PGRAPH_CTXCTL_CODE_INDEX_WRITE_AUTOINCR 0x01000000 +#define NVC0_PGRAPH_CTXCTL_CODE_INDEX_READ_AUTOINCR 0x02000000 +#define NVC0_PGRAPH_CTXCTL_CODE_INDEX_SECRET 0x10000000 +#define NVC0_PGRAPH_CTXCTL_CODE_INDEX_SECRET_LOCKDOWN 0x20000000 +#define NVC0_PGRAPH_CTXCTL_CODE_INDEX_SECRET_FAIL 0x40000000 +#define NVC0_PGRAPH_CTXCTL_CODE_INDEX_SECRET_SCRUBBER_ACTIVE 0x80000000 + +#define NVC0_PGRAPH_CTXCTL_CODE 0x00409184 + +#define NVC0_PGRAPH_CTXCTL_CODE_VIRT_ADDR 0x00409188 +#define NVC0_PGRAPH_CTXCTL_CODE_VIRT_ADDR__SHR 8 + +#define NVC0_PGRAPH_CTXCTL_DATA_INDEX(i0) (0x004091c0 + 0x8*(i0)) +#define NVC0_PGRAPH_CTXCTL_DATA_INDEX__ESIZE 0x00000008 +#define NVC0_PGRAPH_CTXCTL_DATA_INDEX__LEN 0x00000008 +#define NVC0_PGRAPH_CTXCTL_DATA_INDEX_ADDR__MASK 0x0000fffc +#define NVC0_PGRAPH_CTXCTL_DATA_INDEX_ADDR__SHIFT 2 +#define NVC0_PGRAPH_CTXCTL_DATA_INDEX_ADDR__SHR 2 +#define NVC0_PGRAPH_CTXCTL_DATA_INDEX_WRITE_AUTOINCR 0x01000000 +#define NVC0_PGRAPH_CTXCTL_DATA_INDEX_READ_AUTOINCR 0x02000000 + +#define NVC0_PGRAPH_CTXCTL_DATA(i0) (0x004091c4 + 0x8*(i0)) +#define NVC0_PGRAPH_CTXCTL_DATA__ESIZE 0x00000008 +#define NVC0_PGRAPH_CTXCTL_DATA__LEN 0x00000008 + +#define NVC0_PGRAPH_CTXCTL_PC 0x00409ff0 + +#define NVC0_PGRAPH_CTXCTL_UPLOAD 0x00409ff4 + +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR 0x00409ff8 +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_ADDR__MASK 0x0000fffc +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_ADDR__SHIFT 2 +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_ADDR__SHR 2 +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_SEG__MASK 0x00100000 +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_SEG__SHIFT 20 +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_SEG_DATA 0x00000000 +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_SEG_CODE 0x00100000 +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_READBACK 0x00200000 +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_XFER_BUSY 0x01000000 +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_SECRET 0x10000000 +#define NVC0_PGRAPH_CTXCTL_UPLOAD_ADDR_CODE_BUSY 0x20000000 + +#define NVC0_PGRAPH_CTXCTL_HOST_IO_INDEX 0x00409ffc + +#define NVC0_PGRAPH_CTXCTL_DONE 0x00409400 +#define NVC0_PGRAPH_CTXCTL_DONE_STRAND 0x00000004 +#define NVC0_PGRAPH_CTXCTL_DONE_MMCTX 0x00000020 +#define NVC0_PGRAPH_CTXCTL_DONE_MMIO_RD 0x00000040 +#define NVC0_PGRAPH_CTXCTL_DONE_MMIO_WRS 0x00000080 +#define NVC0_PGRAPH_CTXCTL_DONE_BAR 0x00000100 +#define NVC0_PGRAPH_CTXCTL_DONE_CC_WATCHDOG 0x00000800 +#define NVC0_PGRAPH_CTXCTL_DONE_UNK12 0x00001000 +#define NVC0_PGRAPH_CTXCTL_DONE_UNK13 0x00002000 + +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE 0x00409404 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0__MASK 0x0000003f +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_GPC_UNK2 0x00000002 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_HUB_CHANNEL_SWITCH 0x00000003 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_HUB_UNK4 0x00000004 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_HUB_CTXCTL_DOWN 0x0000000b +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_HUB_UNK12 0x0000000c +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_ZERO 0x00000020 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_STRAND 0x00000022 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_MMCTX 0x00000025 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_MMIO_RD 0x00000026 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_MMIO_WRS 0x00000027 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_BAR 0x00000028 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_CC_WATCHDOG 0x0000002b +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_UNK12 0x0000002c +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC0_UNK13 0x0000002d +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1__MASK 0x00003f00 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1__SHIFT 8 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_GPC_UNK2 0x00000200 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_HUB_CHANNEL_SWITCH 0x00000300 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_HUB_UNK4 0x00000400 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_HUB_CTXCTL_DOWN 0x00000b00 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_HUB_UNK12 0x00000c00 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_ZERO 0x00002000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_STRAND 0x00002200 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_MMCTX 0x00002500 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_MMIO_RD 0x00002600 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_MMIO_WRS 0x00002700 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_BAR 0x00002800 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_CC_WATCHDOG 0x00002b00 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_UNK12 0x00002c00 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_SRC1_UNK13 0x00002d00 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_FUN__MASK 0x00010000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_FUN__SHIFT 16 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_FUN_OR 0x00000000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_FUN_AND 0x00010000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_NOT 0x00020000 +#define NVC0_PGRAPH_CTXCTL_INTR_ROUTE_LEVEL 0x00040000 + +#define NVC0_PGRAPH_CTXCTL_BAR_REQMASK(i0) (0x0040940c + 0x4*(i0)) +#define NVC0_PGRAPH_CTXCTL_BAR_REQMASK__ESIZE 0x00000004 +#define NVC0_PGRAPH_CTXCTL_BAR_REQMASK__LEN 0x00000002 + +#define NVC0_PGRAPH_CTXCTL_BAR 0x00409414 + +#define NVC0_PGRAPH_CTXCTL_BAR_SET 0x00409418 + +#define NVC0_PGRAPH_CTXCTL_CC_WATCHDOG 0x00409430 +#define NVC0_PGRAPH_CTXCTL_CC_WATCHDOG_TIME_REMAINING__MASK 0x3fffffff +#define NVC0_PGRAPH_CTXCTL_CC_WATCHDOG_TIME_REMAINING__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_CC_WATCHDOG_ENABLE 0x80000000 + +#define NVC0_PGRAPH_CTXCTL_WRCMD_DATA 0x00409500 + +#define NVC0_PGRAPH_CTXCTL_WRCMD_CMD 0x00409504 + +#define NVC0_PGRAPH_CTXCTL_NEW_CAPS 0x00409620 +#define NVC0_PGRAPH_CTXCTL_NEW_CAPS_CODE_SIZE__MASK 0x000000ff +#define NVC0_PGRAPH_CTXCTL_NEW_CAPS_CODE_SIZE__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_NEW_CAPS_CODE_SIZE__SHR 8 +#define NVC0_PGRAPH_CTXCTL_NEW_CAPS_DATA_SIZE__MASK 0x0000ff00 +#define NVC0_PGRAPH_CTXCTL_NEW_CAPS_DATA_SIZE__SHIFT 8 +#define NVC0_PGRAPH_CTXCTL_NEW_CAPS_DATA_SIZE__SHR 8 + +#define NVC0_PGRAPH_CTXCTL_MMCTX_SAVE_SWBASE 0x00409700 +#define NVC0_PGRAPH_CTXCTL_MMCTX_SAVE_SWBASE__SHR 8 + +#define NVC0_PGRAPH_CTXCTL_MMCTX_LOAD_SWBASE 0x00409704 +#define NVC0_PGRAPH_CTXCTL_MMCTX_LOAD_SWBASE__SHR 8 + +#define NVC0_PGRAPH_CTXCTL_MMCTX_BASE 0x00409710 + +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL 0x00409714 +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL_QFREE__MASK 0x0000001f +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL_QFREE__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL_QLIMIT__MASK 0x00001f00 +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL_QLIMIT__SHIFT 8 +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL_DIR__MASK 0x00010000 +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL_DIR__SHIFT 16 +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL_DIR_SAVE 0x00000000 +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL_DIR_LOAD 0x00010000 +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL_START_TRIGGER 0x00020000 +#define NVC0_PGRAPH_CTXCTL_MMCTX_CTRL_STOP_TRIGGER 0x00040000 + +#define NVC0_PGRAPH_CTXCTL_MMCTX_MULTI_STRIDE 0x00409718 + +#define NVC0_PGRAPH_CTXCTL_MMCTX_MULTI_MASK 0x0040971c + +#define NVC0_PGRAPH_CTXCTL_MMCTX_QUEUE 0x00409720 +#define NVC0_PGRAPH_CTXCTL_MMCTX_QUEUE_BASE_EN 0x00000001 +#define NVC0_PGRAPH_CTXCTL_MMCTX_QUEUE_MULTI_EN 0x00000002 +#define NVC0_PGRAPH_CTXCTL_MMCTX_QUEUE_ADDR__MASK 0x03fffffc +#define NVC0_PGRAPH_CTXCTL_MMCTX_QUEUE_ADDR__SHIFT 2 +#define NVC0_PGRAPH_CTXCTL_MMCTX_QUEUE_ADDR__SHR 2 +#define NVC0_PGRAPH_CTXCTL_MMCTX_QUEUE_CNTM1__MASK 0xfc000000 +#define NVC0_PGRAPH_CTXCTL_MMCTX_QUEUE_CNTM1__SHIFT 26 + +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL 0x00409728 +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL_UNK0 0x00000001 +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL_ADDR__MASK 0x03fffffc +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL_ADDR__SHIFT 2 +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL_ADDR__SHR 2 +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL_WRS 0x20000000 +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL_ACCESS__MASK 0x40000000 +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL_ACCESS__SHIFT 30 +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL_ACCESS_READ 0x00000000 +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL_ACCESS_WRITE 0x40000000 +#define NVC0_PGRAPH_CTXCTL_MMIO_CTRL_TRIGGER 0x80000000 + +#define NVC0_PGRAPH_CTXCTL_MMIO_RDVAL 0x0040972c + +#define NVC0_PGRAPH_CTXCTL_MMIO_WRVAL 0x00409730 + +#define NVC0_PGRAPH_CTXCTL_MMCTX_LOAD_COUNT 0x0040974c + +#define NVC0_PGRAPH_CTXCTL_CC_SCRATCH(i0) (0x00409800 + 0x4*(i0)) +#define NVC0_PGRAPH_CTXCTL_CC_SCRATCH__ESIZE 0x00000004 +#define NVC0_PGRAPH_CTXCTL_CC_SCRATCH__LEN 0x00000008 + +#define NVC0_PGRAPH_CTXCTL_CC_SCRATCH_SET(i0) (0x00409820 + 0x4*(i0)) +#define NVC0_PGRAPH_CTXCTL_CC_SCRATCH_SET__ESIZE 0x00000004 +#define NVC0_PGRAPH_CTXCTL_CC_SCRATCH_SET__LEN 0x00000008 + +#define NVC0_PGRAPH_CTXCTL_CC_SCRATCH_CLEAR(i0) (0x00409840 + 0x4*(i0)) +#define NVC0_PGRAPH_CTXCTL_CC_SCRATCH_CLEAR__ESIZE 0x00000004 +#define NVC0_PGRAPH_CTXCTL_CC_SCRATCH_CLEAR__LEN 0x00000008 + +#define NVC0_PGRAPH_CTXCTL_STRANDS 0x00409880 + +#define NVC0_PGRAPH_CTXCTL_STRAND_SAVE_SWBASE 0x00409908 +#define NVC0_PGRAPH_CTXCTL_STRAND_SAVE_SWBASE__SHR 8 + +#define NVC0_PGRAPH_CTXCTL_STRAND_LOAD_SWBASE 0x0040990c +#define NVC0_PGRAPH_CTXCTL_STRAND_LOAD_SWBASE__SHR 8 + +#define NVC0_PGRAPH_CTXCTL_STRAND_SIZE 0x00409910 + +#define NVC0_PGRAPH_CTXCTL_STRAND_GENE_CNT 0x00409918 + +#define NVC0_PGRAPH_CTXCTL_STRAND_FIRST_GENE 0x0040991c + +#define NVC0_PGRAPH_CTXCTL_STRAND_CMD 0x00409928 +#define NVC0_PGRAPH_CTXCTL_STRAND_CMD_LATCH_FIRST_GENE 0x00000001 +#define NVC0_PGRAPH_CTXCTL_STRAND_CMD_LATCH_GENE_CNT 0x00000002 +#define NVC0_PGRAPH_CTXCTL_STRAND_CMD_SAVE 0x00000003 +#define NVC0_PGRAPH_CTXCTL_STRAND_CMD_LOAD 0x00000004 +#define NVC0_PGRAPH_CTXCTL_STRAND_CMD_UNK5 0x00000005 +#define NVC0_PGRAPH_CTXCTL_STRAND_CMD_UNKA 0x0000000a +#define NVC0_PGRAPH_CTXCTL_STRAND_CMD_UNKB 0x0000000b +#define NVC0_PGRAPH_CTXCTL_STRAND_CMD_UNKC 0x0000000c +#define NVC0_PGRAPH_CTXCTL_STRAND_CMD_UNKD 0x0000000d + +#define NVC0_PGRAPH_CTXCTL_MEM_BASE 0x00409a04 +#define NVC0_PGRAPH_CTXCTL_MEM_BASE__SHR 8 + +#define NVC0_PGRAPH_CTXCTL_MEM_CHAN 0x00409a0c +#define NVC0_PGRAPH_CTXCTL_MEM_CHAN_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_CTXCTL_MEM_CHAN_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_MEM_CHAN_ADDRESS__SHR 12 +#define NVC0_PGRAPH_CTXCTL_MEM_CHAN_TARGET__MASK 0x30000000 +#define NVC0_PGRAPH_CTXCTL_MEM_CHAN_TARGET__SHIFT 28 +#define NVC0_PGRAPH_CTXCTL_MEM_CHAN_TARGET_VRAM 0x00000000 +#define NVC0_PGRAPH_CTXCTL_MEM_CHAN_TARGET_SYSRAM 0x20000000 +#define NVC0_PGRAPH_CTXCTL_MEM_CHAN_TARGET_SYSRAM_NO_SNOOP 0x30000000 + +#define NVC0_PGRAPH_CTXCTL_MEM_CMD 0x00409a10 +#define NVC0_PGRAPH_CTXCTL_MEM_CMD_LOAD_CHAN 0x00000007 + +#define NVC0_PGRAPH_CTXCTL_MEM_TARGET 0x00409a20 +#define NVC0_PGRAPH_CTXCTL_MEM_TARGET_TARGET__MASK 0x0000001f +#define NVC0_PGRAPH_CTXCTL_MEM_TARGET_TARGET__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_MEM_TARGET_TARGET_VM 0x00000001 +#define NVC0_PGRAPH_CTXCTL_MEM_TARGET_TARGET_VRAM 0x00000002 +#define NVC0_PGRAPH_CTXCTL_MEM_TARGET_TARGET_SYSRAM_NOSNOOP 0x00000003 +#define NVC0_PGRAPH_CTXCTL_MEM_TARGET_TARGET_SYSRAM 0x00000004 +#define NVC0_PGRAPH_CTXCTL_MEM_TARGET_UNK31 0x80000000 + +#define NVC0_PGRAPH_CTXCTL_UNITS 0x00409604 +#define NVC0_PGRAPH_CTXCTL_UNITS_GPC_COUNT__MASK 0x0000001f +#define NVC0_PGRAPH_CTXCTL_UNITS_GPC_COUNT__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_UNITS_ROPC_COUNT__MASK 0x001f0000 +#define NVC0_PGRAPH_CTXCTL_UNITS_ROPC_COUNT__SHIFT 16 + +#define NVC0_PGRAPH_CTXCTL_RED_SWITCH 0x00409614 +#define NVC0_PGRAPH_CTXCTL_RED_SWITCH_UNK0_MAIN 0x00000001 +#define NVC0_PGRAPH_CTXCTL_RED_SWITCH_UNK0_GPC 0x00000002 +#define NVC0_PGRAPH_CTXCTL_RED_SWITCH_POWER_MAIN 0x00000010 +#define NVC0_PGRAPH_CTXCTL_RED_SWITCH_POWER_GPC 0x00000020 +#define NVC0_PGRAPH_CTXCTL_RED_SWITCH_POWER_ROPC 0x00000040 +#define NVC0_PGRAPH_CTXCTL_RED_SWITCH_ENABLE_MAIN 0x00000100 +#define NVC0_PGRAPH_CTXCTL_RED_SWITCH_ENABLE_GPC 0x00000200 +#define NVC0_PGRAPH_CTXCTL_RED_SWITCH_ENABLE_ROPC 0x00000400 + +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE 0x00409c14 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0__MASK 0x0000003f +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0__SHIFT 0 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_GPC_UNK2 0x00000002 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_HUB_CHANNEL_SWITCH 0x00000003 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_HUB_UNK4 0x00000004 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_HUB_CTXCTL_DOWN 0x0000000b +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_HUB_UNK12 0x0000000c +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_ZERO 0x00000020 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_STRAND 0x00000022 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_MMCTX 0x00000025 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_MMIO_RD 0x00000026 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_MMIO_WRS 0x00000027 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_BAR 0x00000028 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_CC_WATCHDOG 0x0000002b +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_UNK12 0x0000002c +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC0_UNK13 0x0000002d +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1__MASK 0x00003f00 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1__SHIFT 8 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_GPC_UNK2 0x00000200 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_HUB_CHANNEL_SWITCH 0x00000300 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_HUB_UNK4 0x00000400 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_HUB_CTXCTL_DOWN 0x00000b00 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_HUB_UNK12 0x00000c00 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_ZERO 0x00002000 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_STRAND 0x00002200 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_MMCTX 0x00002500 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_MMIO_RD 0x00002600 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_MMIO_WRS 0x00002700 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_BAR 0x00002800 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_CC_WATCHDOG 0x00002b00 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_UNK12 0x00002c00 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_SRC1_UNK13 0x00002d00 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_FUN__MASK 0x00010000 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_FUN__SHIFT 16 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_FUN_OR 0x00000000 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_FUN_AND 0x00010000 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_NOT 0x00020000 +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ROUTE_LEVEL 0x00040000 + +#define NVC0_PGRAPH_CTXCTL_INTR_UP_STATUS 0x00409c18 + +#define NVC0_PGRAPH_CTXCTL_INTR_UP_SET 0x00409c1c + +#define NVC0_PGRAPH_CTXCTL_INTR_UP_CLEAR 0x00409c20 + +#define NVC0_PGRAPH_CTXCTL_INTR_UP_ENABLE 0x00409c24 + +#define NVC0_PGRAPH_ROPC_BROADCAST 0x00408800 +#define NVC0_PGRAPH_ROPC_BROADCAST__ESIZE 0x00000400 + + +#define NVC0_PGRAPH_ROPC_BROADCAST_ZROP 0x00408800 +#define NVC0_PGRAPH_ROPC_BROADCAST_ZROP__ESIZE 0x00000100 + +#define NVC0_PGRAPH_ROPC_BROADCAST_ZROP_TRAP 0x00408870 +#define NVC0_PGRAPH_ROPC_BROADCAST_ZROP_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_ROPC_BROADCAST_ZROP_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_ROPC_BROADCAST_CROP 0x00408900 +#define NVC0_PGRAPH_ROPC_BROADCAST_CROP__ESIZE 0x00000100 + +#define NVC0_PGRAPH_ROPC_BROADCAST_CROP_TRAP 0x00408944 +#define NVC0_PGRAPH_ROPC_BROADCAST_CROP_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_ROPC_BROADCAST_CROP_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_ROPC_BROADCAST_TRAP 0x00408a04 +#define NVC0_PGRAPH_ROPC_BROADCAST_TRAP_CROP 0x00000001 +#define NVC0_PGRAPH_ROPC_BROADCAST_TRAP_ZROP 0x00000002 + +#define NVC0_PGRAPH_ROPC_BROADCAST_TRAP_EN 0x00408a08 +#define NVC0_PGRAPH_ROPC_BROADCAST_TRAP_EN_CROP 0x00000001 +#define NVC0_PGRAPH_ROPC_BROADCAST_TRAP_EN_ZROP 0x00000002 + +#define NVC0_PGRAPH_ROPC_BROADCAST_RED_SWITCH 0x00408a10 +#define NVC0_PGRAPH_ROPC_BROADCAST_RED_SWITCH_UNK0_ROPC 0x00000004 +#define NVC0_PGRAPH_ROPC_BROADCAST_RED_SWITCH_POWER_ROPC 0x00000040 +#define NVC0_PGRAPH_ROPC_BROADCAST_RED_SWITCH_ENABLE_ROPC 0x00000400 + +#define NVC0_PGRAPH_ROPC(i0) (0x00410000 + 0x400*(i0)) +#define NVC0_PGRAPH_ROPC__ESIZE 0x00000400 +#define NVC0_PGRAPH_ROPC__LEN 0x00000008 + + +#define NVC0_PGRAPH_ROPC_ZROP(i0) (0x00410000 + 0x400*(i0)) +#define NVC0_PGRAPH_ROPC_ZROP__ESIZE 0x00000100 + +#define NVC0_PGRAPH_ROPC_ZROP_TRAP(i0) (0x00410070 + 0x400*(i0)) +#define NVC0_PGRAPH_ROPC_ZROP_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_ROPC_ZROP_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_ROPC_CROP(i0) (0x00410100 + 0x400*(i0)) +#define NVC0_PGRAPH_ROPC_CROP__ESIZE 0x00000100 + +#define NVC0_PGRAPH_ROPC_CROP_TRAP(i0) (0x00410144 + 0x400*(i0)) +#define NVC0_PGRAPH_ROPC_CROP_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_ROPC_CROP_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_ROPC_TRAP(i0) (0x00410204 + 0x400*(i0)) +#define NVC0_PGRAPH_ROPC_TRAP_CROP 0x00000001 +#define NVC0_PGRAPH_ROPC_TRAP_ZROP 0x00000002 + +#define NVC0_PGRAPH_ROPC_TRAP_EN(i0) (0x00410208 + 0x400*(i0)) +#define NVC0_PGRAPH_ROPC_TRAP_EN_CROP 0x00000001 +#define NVC0_PGRAPH_ROPC_TRAP_EN_ZROP 0x00000002 + +#define NVC0_PGRAPH_ROPC_RED_SWITCH(i0) (0x00410210 + 0x400*(i0)) +#define NVC0_PGRAPH_ROPC_RED_SWITCH_UNK0_ROPC 0x00000004 +#define NVC0_PGRAPH_ROPC_RED_SWITCH_POWER_ROPC 0x00000040 +#define NVC0_PGRAPH_ROPC_RED_SWITCH_ENABLE_ROPC 0x00000400 + +#define NVC0_PGRAPH_GPC_BROADCAST 0x00418000 +#define NVC0_PGRAPH_GPC_BROADCAST__ESIZE 0x00008000 + + +#define NVC0_PGRAPH_GPC_BROADCAST_UNK380 0x00418380 +#define NVC0_PGRAPH_GPC_BROADCAST_UNK380__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_PROP 0x00418400 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP 0x00418420 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_RT_PITCH_OVERRUN 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_RT_WIDTH_OVERRUN 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_RT_HEIGHT_OVERRUN 0x00000020 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_ZETA_STORAGE_TYPE_MISMATCH 0x00000080 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_RT_STORAGE_TYPE_MISMATCH 0x00000100 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_RT_LINEAR_MISMATCH 0x00000400 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_5 0x00418434 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_5_X__MASK 0x0000ffff +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_5_X__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_5_Y__MASK 0xffff0000 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_5_Y__SHIFT 16 + +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_6 0x00418438 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_6_FORMAT__MASK 0x00003f00 +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_6_FORMAT__SHIFT 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_7 0x0041843c +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_7_STORAGE_TYPE__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_BROADCAST_PROP_TRAP_7_STORAGE_TYPE__SHIFT 0 + +#define NVC0_PGRAPH_GPC_BROADCAST_UNK500 0x00418500 +#define NVC0_PGRAPH_GPC_BROADCAST_UNK500__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_UNK600 0x00418600 +#define NVC0_PGRAPH_GPC_BROADCAST_UNK600__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_UNK680 0x00418680 +#define NVC0_PGRAPH_GPC_BROADCAST_UNK680__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_UNK700 0x00418700 +#define NVC0_PGRAPH_GPC_BROADCAST_UNK700__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP 0x00418800 +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_HUB2ESETUP_ADDR 0x00418808 +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_HUB2ESETUP_ADDR__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_HUB2ESETUP_CONF 0x0041880c +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_HUB2ESETUP_CONF_UNK0__MASK 0x000007ff +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_HUB2ESETUP_CONF_UNK0__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_HUB2ESETUP_CONF_UNK31 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_POLY2ESETUP 0x00418810 +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_POLY2ESETUP_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_POLY2ESETUP_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_POLY2ESETUP_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_POLY2ESETUP_UNK31 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_TRAP 0x00418824 +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_ESETUP_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_FFB 0x00418880 +#define NVC0_PGRAPH_GPC_BROADCAST_FFB__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_FFB_PART_CONFIG 0x004188ac +#define NVC0_PGRAPH_GPC_BROADCAST_FFB_PART_CONFIG_PART_COUNT__MASK 0x0000000f +#define NVC0_PGRAPH_GPC_BROADCAST_FFB_PART_CONFIG_PART_COUNT__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_FFB_PART_CONFIG_MEM_SPLIT_ENABLE 0x00000010 + +#define NVC0_PGRAPH_GPC_BROADCAST_FFB_UNK34_ADDR 0x004188b4 +#define NVC0_PGRAPH_GPC_BROADCAST_FFB_UNK34_ADDR__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_FFB_UNK38_ADDR 0x004188b8 +#define NVC0_PGRAPH_GPC_BROADCAST_FFB_UNK38_ADDR__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_ZCULL 0x00418900 +#define NVC0_PGRAPH_GPC_BROADCAST_ZCULL__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_ZCULL_TRAP 0x00418900 +#define NVC0_PGRAPH_GPC_BROADCAST_ZCULL_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_ZCULL_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_UNK980 0x00418980 +#define NVC0_PGRAPH_GPC_BROADCAST_UNK980__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_UNKA00 0x00418a00 +#define NVC0_PGRAPH_GPC_BROADCAST_UNKA00__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS 0x00418b00 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID(i0) (0x00418b08 + 0x4*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID__LEN 0x0000002c +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_0__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_0__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_1__MASK 0x000003e0 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_1__SHIFT 5 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_2__MASK 0x00007c00 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_2__SHIFT 10 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_3__MASK 0x000f8000 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_3__SHIFT 15 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_4__MASK 0x01f00000 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_4__SHIFT 20 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_5__MASK 0x3e000000 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TP_GPCID_5__SHIFT 25 + +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TOTAL 0x00418bb8 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TOTAL_ROPC_COUNT__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TOTAL_ROPC_COUNT__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TOTAL_GPC_COUNT__MASK 0x0000ff00 +#define NVC0_PGRAPH_GPC_BROADCAST_TPBUS_TOTAL_GPC_COUNT__SHIFT 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_TPCONF 0x00418c00 +#define NVC0_PGRAPH_GPC_BROADCAST_TPCONF__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_TPCONF_TPCNT 0x00418c08 + +#define NVC0_PGRAPH_GPC_BROADCAST_TPCONF_TPID(i0) (0x00418c10 + 0x4*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TPCONF_TPID__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TPCONF_TPID__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_UNKC80 0x00418c80 +#define NVC0_PGRAPH_GPC_BROADCAST_UNKC80__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_UNKC80_TPCNT 0x00418c8c + +#define NVC0_PGRAPH_GPC_BROADCAST_UNKD00 0x00418d00 +#define NVC0_PGRAPH_GPC_BROADCAST_UNKD00__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_UNKE00 0x00418e00 +#define NVC0_PGRAPH_GPC_BROADCAST_UNKE00__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_UNKF00 0x00418f00 +#define NVC0_PGRAPH_GPC_BROADCAST_UNKF00__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_CCACHE 0x00419000 +#define NVC0_PGRAPH_GPC_BROADCAST_CCACHE__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_CCACHE_HUB2GPC_ADDR 0x00419004 +#define NVC0_PGRAPH_GPC_BROADCAST_CCACHE_HUB2GPC_ADDR__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_CCACHE_HUB2GPC_CONF 0x00419008 +#define NVC0_PGRAPH_GPC_BROADCAST_CCACHE_HUB2GPC_CONF_UNK0__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_BROADCAST_CCACHE_HUB2GPC_CONF_UNK0__SHIFT 0 + +#define NVC0_PGRAPH_GPC_BROADCAST_CCACHE_TRAP 0x00419028 +#define NVC0_PGRAPH_GPC_BROADCAST_CCACHE_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CCACHE_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST 0x00419800 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST__ESIZE 0x00000800 + + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY 0x00419800 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY__ESIZE 0x00000200 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY_POLY2ESETUP 0x00419848 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY_POLY2ESETUP_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY_POLY2ESETUP_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY_POLY2ESETUP_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY_POLY2ESETUP_UNK28 0x10000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY_TRAP 0x00419884 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_POLY_TPID 0x00419888 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TEX 0x00419a00 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TEX__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TEX_TRAP 0x00419a24 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TEX_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TEX_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS 0x00419b00 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID(i0) (0x00419b00 + 0x4*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID__LEN 0x0000002c +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_0__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_0__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_1__MASK 0x000003e0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_1__SHIFT 5 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_2__MASK 0x00007c00 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_2__SHIFT 10 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_3__MASK 0x000f8000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_3__SHIFT 15 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_4__MASK 0x01f00000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_4__SHIFT 20 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_5__MASK 0x3e000000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_TP_GPCID_5__SHIFT 25 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_UNKD0 0x00419bd0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_UNKD0_ROPC_COUNT__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_UNKD0_ROPC_COUNT__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_UNKD0_GPC_COUNT__MASK 0x0000ff00 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_UNKD0_GPC_COUNT__SHIFT 8 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_UNKD0_UNK16__MASK 0x1fff0000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_UNKD0_UNK16__SHIFT 16 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_UNKE4 0x00419be4 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_UNKE4_UNK0__MASK 0x3fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TPBUS_UNKE4_UNK0__SHIFT 0 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_L1 0x00419c80 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_L1__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_L1_TRAP 0x00419c8c +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_L1_TRAP_GLOBAL_MAP_READ 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_L1_TRAP_GLOBAL_MAP_WRITE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_L1_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_L1_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_L1_TPID 0x00419ce8 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TRAP 0x00419d08 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TRAP_TEX 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TRAP_MP 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TRAP_POLY 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TRAP_L1C 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TRAP_EN 0x00419d0c +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TRAP_EN_TEX 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TRAP_EN_MP 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TRAP_EN_POLY 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_TRAP_EN_L1C 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP 0x00419e00 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP__ESIZE 0x00000200 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_UNK44_TRAP 0x00419e44 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_UNK4C_TRAP 0x00419e4c + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_TRAP_HANDLER_PC 0x00419e58 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_OP(i0) (0x00419e60 + 0x4*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_OP__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_OP__LEN 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_OP_0__MASK 0x0000ffff +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_OP_0__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_OP_1__MASK 0xffff0000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_OP_1__SHIFT 16 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW 0x00419e70 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_0 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_1 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_2 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_3 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_4 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_5 0x00000020 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_6 0x00000040 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_7 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER(i0) (0x00419e74 + 0x4*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_PM_COUNTER__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_BROADCAST_MP_TPID 0x00419e98 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL 0x0041a000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL__ESIZE 0x00001000 + + + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_TRIGGER 0x0041a000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_TRIGGER_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_TRIGGER_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_TRIGGER_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_TRIGGER_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_TRIGGER_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_TRIGGER_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_TRIGGER_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ACK 0x0041a004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ACK_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ACK_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ACK_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ACK_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ACK_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ACK_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ACK_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR 0x0041a008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_SET 0x0041a010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_SET_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_SET_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_SET_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_SET_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_SET_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_SET_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_SET_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_CLR 0x0041a014 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_CLR_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_CLR_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_CLR_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_CLR_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_CLR_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_CLR_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_CLR_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN 0x0041a018 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_EN_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING 0x0041a01c +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M1__MASK 0x0000ffff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M1__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M1_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M1_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M1_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M1_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M1_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M1_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M1_XFER_FAULT 0x00000200 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M2__MASK 0xffff0000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M2__SHIFT 16 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M2_PERIODIC 0x00010000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M2_WATCHDOG 0x00020000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M2_FIFO_DATA 0x00040000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M2_CHANNEL_SWITCH 0x00080000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M2_EXIT 0x00100000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M2_USER1 0x00400000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTING_M2_XFER_FAULT 0x02000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_PERIODIC_PERIOD 0x0041a020 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_PERIODIC_TIME 0x0041a024 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_PERIODIC_ENABLE 0x0041a028 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TIME_LOW 0x0041a02c + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TIME_HIGH 0x0041a030 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_WATCHDOG_TIME 0x0041a034 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_WATCHDOG_ENABLE 0x0041a038 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_SCRATCH(i0) (0x0041a040 + 0x4*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_SCRATCH__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_SCRATCH__LEN 0x00000002 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_ACCESS_EN 0x0041a048 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_ACCESS_EN_CHANNEL_SWITCH 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_ACCESS_EN_FIFO 0x00000002 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR 0x0041a050 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_CHAN__MASK 0x3fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_CHAN__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_CHAN_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_CHAN_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_CHAN_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_CHAN_TARGET__MASK 0x30000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_CHAN_TARGET__SHIFT 28 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_CHAN_TARGET_VRAM 0x00000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_CHAN_TARGET_SYSRAM 0x20000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_CHAN_TARGET_SYSRAM_NO_SNOOP 0x30000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_CUR_VALID 0x40000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT 0x0041a054 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_CHAN__MASK 0x3fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_CHAN__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_CHAN_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_CHAN_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_CHAN_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_CHAN_TARGET__MASK 0x30000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_CHAN_TARGET__SHIFT 28 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_CHAN_TARGET_VRAM 0x00000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_CHAN_TARGET_SYSRAM 0x20000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_CHAN_TARGET_SYSRAM_NO_SNOOP 0x30000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_NEXT_VALID 0x40000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_TRIGGER 0x0041a054 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_TRIGGER_UNLOAD 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CHANNEL_TRIGGER_LOAD 0x00000002 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_DATA 0x0041a064 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_CMD 0x0041a068 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_CMD_MTHD__MASK 0x000007ff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_CMD_MTHD__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_CMD_MTHD__SHR 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_CMD_SUBC__MASK 0x00003800 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_CMD_SUBC__SHIFT 11 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_CMD_NONINCR 0x00004000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_OCCUPIED 0x0041a070 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_ACK 0x0041a074 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_FIFO_LIMIT 0x0041a078 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MISC_TRIGGER 0x0041a088 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MISC_TRIGGER_WRCACHE_FLUSH 0x00010000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MISC_TRIGGER_PM_TRIGGER 0x00020000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_CTRL 0x0041a100 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_CTRL_START_TRIGGER 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_CTRL_RESET_UNK2_TRIGGER 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_CTRL_RESET_UNK3_TRIGGER 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_CTRL_STOPPED 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_CTRL_SLEEPING 0x00000020 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_ENTRY 0x0041a104 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS 0x0041a108 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS_CODE_SIZE__MASK 0x000001ff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS_CODE_SIZE__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS_CODE_SIZE__SHR 8 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS_DATA_SIZE__MASK 0x0001fe00 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS_DATA_SIZE__SHIFT 9 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS_DATA_SIZE__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_EXT_BASE 0x0041a110 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_EXT_BASE__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_FUC_ADDR 0x0041a114 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL 0x0041a118 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_FULL 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SEG__MASK 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SEG__SHIFT 4 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SEG_DATA 0x00000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SEG_CODE 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_DIR__MASK 0x00000020 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_DIR__SHIFT 5 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_DIR_LOAD 0x00000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_DIR_STORE 0x00000020 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SIZE__MASK 0x00000700 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SIZE__SHIFT 8 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SIZE_16 0x00000200 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SIZE_32 0x00000300 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SIZE_64 0x00000400 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SIZE_128 0x00000500 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_SIZE_256 0x00000600 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_TARGET__MASK 0x00007000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_CTRL_TARGET__SHIFT 12 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_EXT_ADDR 0x0041a11c + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_STATUS 0x0041a120 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_STATUS_PENDING 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_STATUS_UNK4__MASK 0x00000030 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_STATUS_UNK4__SHIFT 4 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_STATUS_STORES_PENDING__MASK 0x00070000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_STATUS_STORES_PENDING__SHIFT 16 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_STATUS_LOADS_PENDING__MASK 0x07000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_XFER_STATUS_LOADS_PENDING__SHIFT 24 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_STATUS 0x0041a128 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_STATUS_XCLD_IDLE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_STATUS_CRYPT_IDLE 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_STATUS_TRAP_ACTIVE 0x00000100 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_STATUS_XDST_IDLE 0x00040000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UC_STATUS_XDLD_IDLE 0x00080000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2 0x0041a12c +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2_UNK0__MASK 0x0000000f +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2_UNK0__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2_SECRETFUL__MASK 0x000000f0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2_SECRETFUL__SHIFT 4 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2_CODE_PORTS__MASK 0x00000f00 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2_CODE_PORTS__SHIFT 8 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2_DATA_PORTS__MASK 0x0000f000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2_DATA_PORTS__SHIFT 12 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2_VM_PAGES_LOG2__MASK 0x000f0000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CAPS2_VM_PAGES_LOG2__SHIFT 16 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TLB_CMD 0x0041a140 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TLB_CMD_PARAM__MASK 0x00ffffff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TLB_CMD_PARAM__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TLB_CMD_CMD__MASK 0x03000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TLB_CMD_CMD__SHIFT 24 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TLB_CMD_CMD_ITLB 0x01000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TLB_CMD_CMD_PTLB 0x02000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TLB_CMD_CMD_VTLB 0x03000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TLB_CMD_RES 0x0041a144 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_INDEX 0x0041a180 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_INDEX_PHYS_ADDR__MASK 0x0000fffc +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_INDEX_PHYS_ADDR__SHIFT 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_INDEX_PHYS_ADDR__SHR 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_INDEX_WRITE_AUTOINCR 0x01000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_INDEX_READ_AUTOINCR 0x02000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_INDEX_SECRET 0x10000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_INDEX_SECRET_LOCKDOWN 0x20000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_INDEX_SECRET_FAIL 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_INDEX_SECRET_SCRUBBER_ACTIVE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE 0x0041a184 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_VIRT_ADDR 0x0041a188 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CODE_VIRT_ADDR__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA_INDEX(i0) (0x0041a1c0 + 0x8*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA_INDEX__ESIZE 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA_INDEX__LEN 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA_INDEX_ADDR__MASK 0x0000fffc +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA_INDEX_ADDR__SHIFT 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA_INDEX_ADDR__SHR 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA_INDEX_WRITE_AUTOINCR 0x01000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA_INDEX_READ_AUTOINCR 0x02000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA(i0) (0x0041a1c4 + 0x8*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA__ESIZE 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DATA__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_PC 0x0041aff0 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD 0x0041aff4 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR 0x0041aff8 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_ADDR__MASK 0x0000fffc +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_ADDR__SHIFT 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_ADDR__SHR 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_SEG__MASK 0x00100000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_SEG__SHIFT 20 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_SEG_DATA 0x00000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_SEG_CODE 0x00100000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_READBACK 0x00200000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_XFER_BUSY 0x01000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_SECRET 0x10000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UPLOAD_ADDR_CODE_BUSY 0x20000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_HOST_IO_INDEX 0x0041affc + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DONE 0x0041a400 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DONE_STRAND 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DONE_MMCTX 0x00000020 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DONE_MMIO_RD 0x00000040 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DONE_MMIO_WRS 0x00000080 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DONE_BAR 0x00000100 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DONE_CC_WATCHDOG 0x00000800 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DONE_UNK12 0x00001000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_DONE_UNK13 0x00002000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE 0x0041a404 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0__MASK 0x0000003f +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_GPC_UNK2 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_HUB_CHANNEL_SWITCH 0x00000003 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_HUB_UNK4 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_HUB_CTXCTL_DOWN 0x0000000b +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_HUB_UNK12 0x0000000c +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_ZERO 0x00000020 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_STRAND 0x00000022 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_MMCTX 0x00000025 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_MMIO_RD 0x00000026 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_MMIO_WRS 0x00000027 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_BAR 0x00000028 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_CC_WATCHDOG 0x0000002b +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_UNK12 0x0000002c +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC0_UNK13 0x0000002d +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1__MASK 0x00003f00 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1__SHIFT 8 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_GPC_UNK2 0x00000200 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_HUB_CHANNEL_SWITCH 0x00000300 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_HUB_UNK4 0x00000400 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_HUB_CTXCTL_DOWN 0x00000b00 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_HUB_UNK12 0x00000c00 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_ZERO 0x00002000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_STRAND 0x00002200 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_MMCTX 0x00002500 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_MMIO_RD 0x00002600 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_MMIO_WRS 0x00002700 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_BAR 0x00002800 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_CC_WATCHDOG 0x00002b00 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_UNK12 0x00002c00 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_SRC1_UNK13 0x00002d00 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_FUN__MASK 0x00010000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_FUN__SHIFT 16 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_FUN_OR 0x00000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_FUN_AND 0x00010000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_NOT 0x00020000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_INTR_ROUTE_LEVEL 0x00040000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_BAR_REQMASK(i0) (0x0041a40c + 0x4*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_BAR_REQMASK__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_BAR_REQMASK__LEN 0x00000002 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_BAR 0x0041a414 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_BAR_SET 0x0041a418 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_WATCHDOG 0x0041a430 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_WATCHDOG_TIME_REMAINING__MASK 0x3fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_WATCHDOG_TIME_REMAINING__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_WATCHDOG_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_WRCMD_DATA 0x0041a500 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_WRCMD_CMD 0x0041a504 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_NEW_CAPS 0x0041a620 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_NEW_CAPS_CODE_SIZE__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_NEW_CAPS_CODE_SIZE__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_NEW_CAPS_CODE_SIZE__SHR 8 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_NEW_CAPS_DATA_SIZE__MASK 0x0000ff00 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_NEW_CAPS_DATA_SIZE__SHIFT 8 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_NEW_CAPS_DATA_SIZE__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_SAVE_SWBASE 0x0041a700 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_SAVE_SWBASE__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_LOAD_SWBASE 0x0041a704 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_LOAD_SWBASE__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_BASE 0x0041a710 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL 0x0041a714 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL_QFREE__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL_QFREE__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL_QLIMIT__MASK 0x00001f00 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL_QLIMIT__SHIFT 8 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL_DIR__MASK 0x00010000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL_DIR__SHIFT 16 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL_DIR_SAVE 0x00000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL_DIR_LOAD 0x00010000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL_START_TRIGGER 0x00020000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_CTRL_STOP_TRIGGER 0x00040000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_MULTI_STRIDE 0x0041a718 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_MULTI_MASK 0x0041a71c + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_QUEUE 0x0041a720 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_QUEUE_BASE_EN 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_QUEUE_MULTI_EN 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_QUEUE_ADDR__MASK 0x03fffffc +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_QUEUE_ADDR__SHIFT 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_QUEUE_ADDR__SHR 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_QUEUE_CNTM1__MASK 0xfc000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_QUEUE_CNTM1__SHIFT 26 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL 0x0041a728 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL_UNK0 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL_ADDR__MASK 0x03fffffc +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL_ADDR__SHIFT 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL_ADDR__SHR 2 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL_WRS 0x20000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL_ACCESS__MASK 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL_ACCESS__SHIFT 30 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL_ACCESS_READ 0x00000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL_ACCESS_WRITE 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_CTRL_TRIGGER 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_RDVAL 0x0041a72c + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMIO_WRVAL 0x0041a730 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MMCTX_LOAD_COUNT 0x0041a74c + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_SCRATCH(i0) (0x0041a800 + 0x4*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_SCRATCH__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_SCRATCH__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_SCRATCH_SET(i0) (0x0041a820 + 0x4*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_SCRATCH_SET__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_SCRATCH_SET__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_SCRATCH_CLEAR(i0) (0x0041a840 + 0x4*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_SCRATCH_CLEAR__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_CC_SCRATCH_CLEAR__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRANDS 0x0041a880 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_SAVE_SWBASE 0x0041a908 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_SAVE_SWBASE__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_LOAD_SWBASE 0x0041a90c +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_LOAD_SWBASE__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_SIZE 0x0041a910 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_GENE_CNT 0x0041a918 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_FIRST_GENE 0x0041a91c + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_CMD 0x0041a928 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_CMD_LATCH_FIRST_GENE 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_CMD_LATCH_GENE_CNT 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_CMD_SAVE 0x00000003 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_CMD_LOAD 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_CMD_UNK5 0x00000005 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_CMD_UNKA 0x0000000a +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_CMD_UNKB 0x0000000b +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_CMD_UNKC 0x0000000c +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_STRAND_CMD_UNKD 0x0000000d + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_BASE 0x0041aa04 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_BASE__SHR 8 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CHAN 0x0041aa0c +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CHAN_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CHAN_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CHAN_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CHAN_TARGET__MASK 0x30000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CHAN_TARGET__SHIFT 28 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CHAN_TARGET_VRAM 0x00000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CHAN_TARGET_SYSRAM 0x20000000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CHAN_TARGET_SYSRAM_NO_SNOOP 0x30000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CMD 0x0041aa10 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_CMD_LOAD_CHAN 0x00000007 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_TARGET 0x0041aa20 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_TARGET_TARGET__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_TARGET_TARGET__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_TARGET_TARGET_VM 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_TARGET_TARGET_VRAM 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_TARGET_TARGET_SYSRAM_NOSNOOP 0x00000003 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_TARGET_TARGET_SYSRAM 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MEM_TARGET_UNK31 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UNITS 0x0041a608 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UNITS_TP_COUNT__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UNITS_TP_COUNT__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UNITS_UNK_ZCULL_COUNT__MASK 0x001f0000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_UNITS_UNK_ZCULL_COUNT__SHIFT 16 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_RED_SWITCH 0x0041a614 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_RED_SWITCH_UNK0_GPC 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_RED_SWITCH_POWER_GPC 0x00000020 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_RED_SWITCH_ENABLE_GPC 0x00000200 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_RED_SWITCH_UNK11 0x00000800 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_MYINDEX 0x0041a618 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP 0x0041ac90 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_PROP 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_ZCULL 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_CCACHE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_ESETUP 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_TP__MASK 0x00ff0000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_TP__SHIFT 16 + +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_EN 0x0041ac94 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_EN_PROP 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_EN_ZCULL 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_EN_CCACHE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_EN_ESETUP 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_EN_TP__MASK 0x00ff0000 +#define NVC0_PGRAPH_GPC_BROADCAST_CTXCTL_TRAP_EN_TP__SHIFT 16 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP(i0) (0x0041c000 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP__ESIZE 0x00000800 +#define NVC0_PGRAPH_GPC_BROADCAST_TP__LEN 0x00000004 + + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY(i0) (0x0041c000 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY__ESIZE 0x00000200 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY_POLY2ESETUP(i0) (0x0041c048 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY_POLY2ESETUP_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY_POLY2ESETUP_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY_POLY2ESETUP_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY_POLY2ESETUP_UNK28 0x10000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY_TRAP(i0) (0x0041c084 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_POLY_TPID(i0) (0x0041c088 + 0x800*(i0)) + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TEX(i0) (0x0041c200 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TEX__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TEX_TRAP(i0) (0x0041c224 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TEX_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TEX_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS(i0) (0x0041c300 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID(i0, i1) (0x0041c300 + 0x800*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID__LEN 0x0000002c +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_0__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_0__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_1__MASK 0x000003e0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_1__SHIFT 5 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_2__MASK 0x00007c00 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_2__SHIFT 10 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_3__MASK 0x000f8000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_3__SHIFT 15 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_4__MASK 0x01f00000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_4__SHIFT 20 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_5__MASK 0x3e000000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_TP_GPCID_5__SHIFT 25 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_UNKD0(i0) (0x0041c3d0 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_UNKD0_ROPC_COUNT__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_UNKD0_ROPC_COUNT__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_UNKD0_GPC_COUNT__MASK 0x0000ff00 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_UNKD0_GPC_COUNT__SHIFT 8 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_UNKD0_UNK16__MASK 0x1fff0000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_UNKD0_UNK16__SHIFT 16 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_UNKE4(i0) (0x0041c3e4 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_UNKE4_UNK0__MASK 0x3fffffff +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TPBUS_UNKE4_UNK0__SHIFT 0 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_L1(i0) (0x0041c480 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_L1__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_L1_TRAP(i0) (0x0041c48c + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_L1_TRAP_GLOBAL_MAP_READ 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_L1_TRAP_GLOBAL_MAP_WRITE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_L1_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_L1_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_L1_TPID(i0) (0x0041c4e8 + 0x800*(i0)) + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TRAP(i0) (0x0041c508 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TRAP_TEX 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TRAP_MP 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TRAP_POLY 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TRAP_L1C 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TRAP_EN(i0) (0x0041c50c + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TRAP_EN_TEX 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TRAP_EN_MP 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TRAP_EN_POLY 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_TRAP_EN_L1C 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP(i0) (0x0041c600 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP__ESIZE 0x00000200 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_UNK44_TRAP(i0) (0x0041c644 + 0x800*(i0)) + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_UNK4C_TRAP(i0) (0x0041c64c + 0x800*(i0)) + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_TRAP_HANDLER_PC(i0) (0x0041c658 + 0x800*(i0)) + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_OP(i0, i1) (0x0041c660 + 0x800*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_OP__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_OP__LEN 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_OP_0__MASK 0x0000ffff +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_OP_0__SHIFT 0 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_OP_1__MASK 0xffff0000 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_OP_1__SHIFT 16 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER_OVERFLOW(i0) (0x0041c670 + 0x800*(i0)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER_OVERFLOW_0 0x00000001 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER_OVERFLOW_1 0x00000002 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER_OVERFLOW_2 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER_OVERFLOW_3 0x00000008 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER_OVERFLOW_4 0x00000010 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER_OVERFLOW_5 0x00000020 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER_OVERFLOW_6 0x00000040 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER_OVERFLOW_7 0x00000080 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER(i0, i1) (0x0041c674 + 0x800*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_PM_COUNTER__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_BROADCAST_TP_MP_TPID(i0) (0x0041c698 + 0x800*(i0)) + +#define NVC0_PGRAPH_GPC(i0) (0x00500000 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC__ESIZE 0x00008000 +#define NVC0_PGRAPH_GPC__LEN 0x00000004 + + +#define NVC0_PGRAPH_GPC_UNK380(i0) (0x00500380 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNK380__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_PROP(i0) (0x00500400 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_PROP__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_PROP_TRAP(i0) (0x00500420 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_PROP_TRAP_RT_PITCH_OVERRUN 0x00000002 +#define NVC0_PGRAPH_GPC_PROP_TRAP_RT_WIDTH_OVERRUN 0x00000010 +#define NVC0_PGRAPH_GPC_PROP_TRAP_RT_HEIGHT_OVERRUN 0x00000020 +#define NVC0_PGRAPH_GPC_PROP_TRAP_ZETA_STORAGE_TYPE_MISMATCH 0x00000080 +#define NVC0_PGRAPH_GPC_PROP_TRAP_RT_STORAGE_TYPE_MISMATCH 0x00000100 +#define NVC0_PGRAPH_GPC_PROP_TRAP_RT_LINEAR_MISMATCH 0x00000400 +#define NVC0_PGRAPH_GPC_PROP_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_PROP_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_PROP_TRAP_5(i0) (0x00500434 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_PROP_TRAP_5_X__MASK 0x0000ffff +#define NVC0_PGRAPH_GPC_PROP_TRAP_5_X__SHIFT 0 +#define NVC0_PGRAPH_GPC_PROP_TRAP_5_Y__MASK 0xffff0000 +#define NVC0_PGRAPH_GPC_PROP_TRAP_5_Y__SHIFT 16 + +#define NVC0_PGRAPH_GPC_PROP_TRAP_6(i0) (0x00500438 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_PROP_TRAP_6_FORMAT__MASK 0x00003f00 +#define NVC0_PGRAPH_GPC_PROP_TRAP_6_FORMAT__SHIFT 8 + +#define NVC0_PGRAPH_GPC_PROP_TRAP_7(i0) (0x0050043c + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_PROP_TRAP_7_STORAGE_TYPE__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_PROP_TRAP_7_STORAGE_TYPE__SHIFT 0 + +#define NVC0_PGRAPH_GPC_UNK500(i0) (0x00500500 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNK500__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_UNK600(i0) (0x00500600 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNK600__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_UNK680(i0) (0x00500680 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNK680__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_UNK700(i0) (0x00500700 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNK700__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_ESETUP(i0) (0x00500800 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_ESETUP__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_ESETUP_HUB2ESETUP_ADDR(i0) (0x00500808 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_ESETUP_HUB2ESETUP_ADDR__SHR 8 + +#define NVC0_PGRAPH_GPC_ESETUP_HUB2ESETUP_CONF(i0) (0x0050080c + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_ESETUP_HUB2ESETUP_CONF_UNK0__MASK 0x000007ff +#define NVC0_PGRAPH_GPC_ESETUP_HUB2ESETUP_CONF_UNK0__SHIFT 0 +#define NVC0_PGRAPH_GPC_ESETUP_HUB2ESETUP_CONF_UNK31 0x80000000 + +#define NVC0_PGRAPH_GPC_ESETUP_POLY2ESETUP(i0) (0x00500810 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_ESETUP_POLY2ESETUP_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_ESETUP_POLY2ESETUP_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_ESETUP_POLY2ESETUP_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_ESETUP_POLY2ESETUP_UNK31 0x80000000 + +#define NVC0_PGRAPH_GPC_ESETUP_TRAP(i0) (0x00500824 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_ESETUP_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_ESETUP_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_FFB(i0) (0x00500880 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_FFB__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_FFB_PART_CONFIG(i0) (0x005008ac + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_FFB_PART_CONFIG_PART_COUNT__MASK 0x0000000f +#define NVC0_PGRAPH_GPC_FFB_PART_CONFIG_PART_COUNT__SHIFT 0 +#define NVC0_PGRAPH_GPC_FFB_PART_CONFIG_MEM_SPLIT_ENABLE 0x00000010 + +#define NVC0_PGRAPH_GPC_FFB_UNK34_ADDR(i0) (0x005008b4 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_FFB_UNK34_ADDR__SHR 8 + +#define NVC0_PGRAPH_GPC_FFB_UNK38_ADDR(i0) (0x005008b8 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_FFB_UNK38_ADDR__SHR 8 + +#define NVC0_PGRAPH_GPC_ZCULL(i0) (0x00500900 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_ZCULL__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_ZCULL_TRAP(i0) (0x00500900 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_ZCULL_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_ZCULL_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_UNK980(i0) (0x00500980 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNK980__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_UNKA00(i0) (0x00500a00 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNKA00__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_TPBUS(i0) (0x00500b00 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TPBUS__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID(i0, i1) (0x00500b08 + 0x8000*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID__LEN 0x0000002c +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_0__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_0__SHIFT 0 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_1__MASK 0x000003e0 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_1__SHIFT 5 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_2__MASK 0x00007c00 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_2__SHIFT 10 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_3__MASK 0x000f8000 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_3__SHIFT 15 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_4__MASK 0x01f00000 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_4__SHIFT 20 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_5__MASK 0x3e000000 +#define NVC0_PGRAPH_GPC_TPBUS_TP_GPCID_5__SHIFT 25 + +#define NVC0_PGRAPH_GPC_TPBUS_TOTAL(i0) (0x00500bb8 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TPBUS_TOTAL_ROPC_COUNT__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_TPBUS_TOTAL_ROPC_COUNT__SHIFT 0 +#define NVC0_PGRAPH_GPC_TPBUS_TOTAL_GPC_COUNT__MASK 0x0000ff00 +#define NVC0_PGRAPH_GPC_TPBUS_TOTAL_GPC_COUNT__SHIFT 8 + +#define NVC0_PGRAPH_GPC_TPCONF(i0) (0x00500c00 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TPCONF__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_TPCONF_TPCNT(i0) (0x00500c08 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_TPCONF_TPID(i0, i1) (0x00500c10 + 0x8000*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_TPCONF_TPID__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_TPCONF_TPID__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_UNKC80(i0) (0x00500c80 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNKC80__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_UNKC80_TPCNT(i0) (0x00500c8c + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_UNKD00(i0) (0x00500d00 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNKD00__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_UNKE00(i0) (0x00500e00 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNKE00__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_UNKF00(i0) (0x00500f00 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_UNKF00__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_CCACHE(i0) (0x00501000 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CCACHE__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_CCACHE_HUB2GPC_ADDR(i0) (0x00501004 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CCACHE_HUB2GPC_ADDR__SHR 8 + +#define NVC0_PGRAPH_GPC_CCACHE_HUB2GPC_CONF(i0) (0x00501008 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CCACHE_HUB2GPC_CONF_UNK0__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_CCACHE_HUB2GPC_CONF_UNK0__SHIFT 0 + +#define NVC0_PGRAPH_GPC_CCACHE_TRAP(i0) (0x00501028 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CCACHE_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_CCACHE_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST(i0) (0x00501800 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST__ESIZE 0x00000800 + + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY(i0) (0x00501800 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY__ESIZE 0x00000200 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY_POLY2ESETUP(i0) (0x00501848 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY_POLY2ESETUP_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY_POLY2ESETUP_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY_POLY2ESETUP_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY_POLY2ESETUP_UNK28 0x10000000 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY_TRAP(i0) (0x00501884 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_POLY_TPID(i0) (0x00501888 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TEX(i0) (0x00501a00 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TEX__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TEX_TRAP(i0) (0x00501a24 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TEX_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TEX_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS(i0) (0x00501b00 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID(i0, i1) (0x00501b00 + 0x8000*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID__LEN 0x0000002c +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_0__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_0__SHIFT 0 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_1__MASK 0x000003e0 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_1__SHIFT 5 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_2__MASK 0x00007c00 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_2__SHIFT 10 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_3__MASK 0x000f8000 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_3__SHIFT 15 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_4__MASK 0x01f00000 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_4__SHIFT 20 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_5__MASK 0x3e000000 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_TP_GPCID_5__SHIFT 25 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_UNKD0(i0) (0x00501bd0 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_UNKD0_ROPC_COUNT__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_UNKD0_ROPC_COUNT__SHIFT 0 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_UNKD0_GPC_COUNT__MASK 0x0000ff00 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_UNKD0_GPC_COUNT__SHIFT 8 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_UNKD0_UNK16__MASK 0x1fff0000 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_UNKD0_UNK16__SHIFT 16 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_UNKE4(i0) (0x00501be4 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_UNKE4_UNK0__MASK 0x3fffffff +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TPBUS_UNKE4_UNK0__SHIFT 0 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_L1(i0) (0x00501c80 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_L1__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_L1_TRAP(i0) (0x00501c8c + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_L1_TRAP_GLOBAL_MAP_READ 0x00000002 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_L1_TRAP_GLOBAL_MAP_WRITE 0x00000004 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_L1_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_L1_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_L1_TPID(i0) (0x00501ce8 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TRAP(i0) (0x00501d08 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TRAP_TEX 0x00000001 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TRAP_MP 0x00000002 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TRAP_POLY 0x00000004 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TRAP_L1C 0x00000008 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TRAP_EN(i0) (0x00501d0c + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TRAP_EN_TEX 0x00000001 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TRAP_EN_MP 0x00000002 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TRAP_EN_POLY 0x00000004 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_TRAP_EN_L1C 0x00000008 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP(i0) (0x00501e00 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP__ESIZE 0x00000200 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_UNK44_TRAP(i0) (0x00501e44 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_UNK4C_TRAP(i0) (0x00501e4c + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_TRAP_HANDLER_PC(i0) (0x00501e58 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_OP(i0, i1) (0x00501e60 + 0x8000*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_OP__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_OP__LEN 0x00000004 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_OP_0__MASK 0x0000ffff +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_OP_0__SHIFT 0 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_OP_1__MASK 0xffff0000 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_OP_1__SHIFT 16 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW(i0) (0x00501e70 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_0 0x00000001 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_1 0x00000002 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_2 0x00000004 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_3 0x00000008 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_4 0x00000010 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_5 0x00000020 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_6 0x00000040 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER_OVERFLOW_7 0x00000080 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER(i0, i1) (0x00501e74 + 0x8000*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_PM_COUNTER__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_TP_BROADCAST_MP_TPID(i0) (0x00501e98 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL(i0) (0x00502000 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL__ESIZE 0x00001000 + + + +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_TRIGGER(i0) (0x00502000 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_TRIGGER_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_TRIGGER_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_TRIGGER_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_TRIGGER_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_TRIGGER_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_TRIGGER_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_TRIGGER_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ACK(i0) (0x00502004 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ACK_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ACK_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ACK_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ACK_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ACK_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ACK_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ACK_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_CTXCTL_INTR(i0) (0x00502008 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_SET(i0) (0x00502010 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_SET_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_SET_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_SET_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_SET_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_SET_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_SET_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_SET_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_CLR(i0) (0x00502014 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_CLR_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_CLR_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_CLR_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_CLR_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_CLR_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_CLR_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_CLR_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN(i0) (0x00502018 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_EN_XFER_FAULT 0x00000200 + +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING(i0) (0x0050201c + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M1__MASK 0x0000ffff +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M1__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M1_PERIODIC 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M1_WATCHDOG 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M1_FIFO_DATA 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M1_CHANNEL_SWITCH 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M1_EXIT 0x00000010 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M1_USER1 0x00000040 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M1_XFER_FAULT 0x00000200 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M2__MASK 0xffff0000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M2__SHIFT 16 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M2_PERIODIC 0x00010000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M2_WATCHDOG 0x00020000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M2_FIFO_DATA 0x00040000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M2_CHANNEL_SWITCH 0x00080000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M2_EXIT 0x00100000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M2_USER1 0x00400000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTING_M2_XFER_FAULT 0x02000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_PERIODIC_PERIOD(i0) (0x00502020 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_PERIODIC_TIME(i0) (0x00502024 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_PERIODIC_ENABLE(i0) (0x00502028 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_TIME_LOW(i0) (0x0050202c + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_TIME_HIGH(i0) (0x00502030 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_WATCHDOG_TIME(i0) (0x00502034 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_WATCHDOG_ENABLE(i0) (0x00502038 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_SCRATCH(i0, i1) (0x00502040 + 0x8000*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_CTXCTL_SCRATCH__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_SCRATCH__LEN 0x00000002 + +#define NVC0_PGRAPH_GPC_CTXCTL_ACCESS_EN(i0) (0x00502048 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_ACCESS_EN_CHANNEL_SWITCH 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_ACCESS_EN_FIFO 0x00000002 + +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR(i0) (0x00502050 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_CHAN__MASK 0x3fffffff +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_CHAN__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_CHAN_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_CHAN_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_CHAN_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_CHAN_TARGET__MASK 0x30000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_CHAN_TARGET__SHIFT 28 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_CHAN_TARGET_VRAM 0x00000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_CHAN_TARGET_SYSRAM 0x20000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_CHAN_TARGET_SYSRAM_NO_SNOOP 0x30000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_CUR_VALID 0x40000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT(i0) (0x00502054 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_CHAN__MASK 0x3fffffff +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_CHAN__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_CHAN_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_CHAN_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_CHAN_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_CHAN_TARGET__MASK 0x30000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_CHAN_TARGET__SHIFT 28 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_CHAN_TARGET_VRAM 0x00000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_CHAN_TARGET_SYSRAM 0x20000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_CHAN_TARGET_SYSRAM_NO_SNOOP 0x30000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_NEXT_VALID 0x40000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_TRIGGER(i0) (0x00502054 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_TRIGGER_UNLOAD 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_CHANNEL_TRIGGER_LOAD 0x00000002 + +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_DATA(i0) (0x00502064 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_CMD(i0) (0x00502068 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_CMD_MTHD__MASK 0x000007ff +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_CMD_MTHD__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_CMD_MTHD__SHR 2 +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_CMD_SUBC__MASK 0x00003800 +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_CMD_SUBC__SHIFT 11 +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_CMD_NONINCR 0x00004000 + +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_OCCUPIED(i0) (0x00502070 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_ACK(i0) (0x00502074 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_FIFO_LIMIT(i0) (0x00502078 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_MISC_TRIGGER(i0) (0x00502088 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_MISC_TRIGGER_WRCACHE_FLUSH 0x00010000 +#define NVC0_PGRAPH_GPC_CTXCTL_MISC_TRIGGER_PM_TRIGGER 0x00020000 + +#define NVC0_PGRAPH_GPC_CTXCTL_UC_CTRL(i0) (0x00502100 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_UC_CTRL_START_TRIGGER 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_UC_CTRL_RESET_UNK2_TRIGGER 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_UC_CTRL_RESET_UNK3_TRIGGER 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_UC_CTRL_STOPPED 0x00000010 +#define NVC0_PGRAPH_GPC_CTXCTL_UC_CTRL_SLEEPING 0x00000020 + +#define NVC0_PGRAPH_GPC_CTXCTL_ENTRY(i0) (0x00502104 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS(i0) (0x00502108 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS_CODE_SIZE__MASK 0x000001ff +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS_CODE_SIZE__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS_CODE_SIZE__SHR 8 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS_DATA_SIZE__MASK 0x0001fe00 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS_DATA_SIZE__SHIFT 9 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS_DATA_SIZE__SHR 8 + +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_EXT_BASE(i0) (0x00502110 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_EXT_BASE__SHR 8 + +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_FUC_ADDR(i0) (0x00502114 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL(i0) (0x00502118 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_FULL 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SEG__MASK 0x00000010 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SEG__SHIFT 4 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SEG_DATA 0x00000000 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SEG_CODE 0x00000010 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_DIR__MASK 0x00000020 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_DIR__SHIFT 5 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_DIR_LOAD 0x00000000 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_DIR_STORE 0x00000020 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SIZE__MASK 0x00000700 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SIZE__SHIFT 8 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SIZE_16 0x00000200 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SIZE_32 0x00000300 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SIZE_64 0x00000400 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SIZE_128 0x00000500 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_SIZE_256 0x00000600 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_TARGET__MASK 0x00007000 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_CTRL_TARGET__SHIFT 12 + +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_EXT_ADDR(i0) (0x0050211c + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_STATUS(i0) (0x00502120 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_STATUS_PENDING 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_STATUS_UNK4__MASK 0x00000030 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_STATUS_UNK4__SHIFT 4 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_STATUS_STORES_PENDING__MASK 0x00070000 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_STATUS_STORES_PENDING__SHIFT 16 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_STATUS_LOADS_PENDING__MASK 0x07000000 +#define NVC0_PGRAPH_GPC_CTXCTL_XFER_STATUS_LOADS_PENDING__SHIFT 24 + +#define NVC0_PGRAPH_GPC_CTXCTL_UC_STATUS(i0) (0x00502128 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_UC_STATUS_XCLD_IDLE 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_UC_STATUS_CRYPT_IDLE 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_UC_STATUS_TRAP_ACTIVE 0x00000100 +#define NVC0_PGRAPH_GPC_CTXCTL_UC_STATUS_XDST_IDLE 0x00040000 +#define NVC0_PGRAPH_GPC_CTXCTL_UC_STATUS_XDLD_IDLE 0x00080000 + +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2(i0) (0x0050212c + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2_UNK0__MASK 0x0000000f +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2_UNK0__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2_SECRETFUL__MASK 0x000000f0 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2_SECRETFUL__SHIFT 4 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2_CODE_PORTS__MASK 0x00000f00 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2_CODE_PORTS__SHIFT 8 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2_DATA_PORTS__MASK 0x0000f000 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2_DATA_PORTS__SHIFT 12 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2_VM_PAGES_LOG2__MASK 0x000f0000 +#define NVC0_PGRAPH_GPC_CTXCTL_CAPS2_VM_PAGES_LOG2__SHIFT 16 + +#define NVC0_PGRAPH_GPC_CTXCTL_TLB_CMD(i0) (0x00502140 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_TLB_CMD_PARAM__MASK 0x00ffffff +#define NVC0_PGRAPH_GPC_CTXCTL_TLB_CMD_PARAM__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_TLB_CMD_CMD__MASK 0x03000000 +#define NVC0_PGRAPH_GPC_CTXCTL_TLB_CMD_CMD__SHIFT 24 +#define NVC0_PGRAPH_GPC_CTXCTL_TLB_CMD_CMD_ITLB 0x01000000 +#define NVC0_PGRAPH_GPC_CTXCTL_TLB_CMD_CMD_PTLB 0x02000000 +#define NVC0_PGRAPH_GPC_CTXCTL_TLB_CMD_CMD_VTLB 0x03000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_TLB_CMD_RES(i0) (0x00502144 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_INDEX(i0) (0x00502180 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_INDEX_PHYS_ADDR__MASK 0x0000fffc +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_INDEX_PHYS_ADDR__SHIFT 2 +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_INDEX_PHYS_ADDR__SHR 2 +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_INDEX_WRITE_AUTOINCR 0x01000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_INDEX_READ_AUTOINCR 0x02000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_INDEX_SECRET 0x10000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_INDEX_SECRET_LOCKDOWN 0x20000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_INDEX_SECRET_FAIL 0x40000000 +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_INDEX_SECRET_SCRUBBER_ACTIVE 0x80000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_CODE(i0) (0x00502184 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_VIRT_ADDR(i0) (0x00502188 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_CODE_VIRT_ADDR__SHR 8 + +#define NVC0_PGRAPH_GPC_CTXCTL_DATA_INDEX(i0, i1) (0x005021c0 + 0x8000*(i0) + 0x8*(i1)) +#define NVC0_PGRAPH_GPC_CTXCTL_DATA_INDEX__ESIZE 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_DATA_INDEX__LEN 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_DATA_INDEX_ADDR__MASK 0x0000fffc +#define NVC0_PGRAPH_GPC_CTXCTL_DATA_INDEX_ADDR__SHIFT 2 +#define NVC0_PGRAPH_GPC_CTXCTL_DATA_INDEX_ADDR__SHR 2 +#define NVC0_PGRAPH_GPC_CTXCTL_DATA_INDEX_WRITE_AUTOINCR 0x01000000 +#define NVC0_PGRAPH_GPC_CTXCTL_DATA_INDEX_READ_AUTOINCR 0x02000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_DATA(i0, i1) (0x005021c4 + 0x8000*(i0) + 0x8*(i1)) +#define NVC0_PGRAPH_GPC_CTXCTL_DATA__ESIZE 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_DATA__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_CTXCTL_PC(i0) (0x00502ff0 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD(i0) (0x00502ff4 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR(i0) (0x00502ff8 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_ADDR__MASK 0x0000fffc +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_ADDR__SHIFT 2 +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_ADDR__SHR 2 +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_SEG__MASK 0x00100000 +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_SEG__SHIFT 20 +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_SEG_DATA 0x00000000 +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_SEG_CODE 0x00100000 +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_READBACK 0x00200000 +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_XFER_BUSY 0x01000000 +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_SECRET 0x10000000 +#define NVC0_PGRAPH_GPC_CTXCTL_UPLOAD_ADDR_CODE_BUSY 0x20000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_HOST_IO_INDEX(i0) (0x00502ffc + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_DONE(i0) (0x00502400 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_DONE_STRAND 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_DONE_MMCTX 0x00000020 +#define NVC0_PGRAPH_GPC_CTXCTL_DONE_MMIO_RD 0x00000040 +#define NVC0_PGRAPH_GPC_CTXCTL_DONE_MMIO_WRS 0x00000080 +#define NVC0_PGRAPH_GPC_CTXCTL_DONE_BAR 0x00000100 +#define NVC0_PGRAPH_GPC_CTXCTL_DONE_CC_WATCHDOG 0x00000800 +#define NVC0_PGRAPH_GPC_CTXCTL_DONE_UNK12 0x00001000 +#define NVC0_PGRAPH_GPC_CTXCTL_DONE_UNK13 0x00002000 + +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE(i0) (0x00502404 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0__MASK 0x0000003f +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_GPC_UNK2 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_HUB_CHANNEL_SWITCH 0x00000003 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_HUB_UNK4 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_HUB_CTXCTL_DOWN 0x0000000b +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_HUB_UNK12 0x0000000c +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_ZERO 0x00000020 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_STRAND 0x00000022 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_MMCTX 0x00000025 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_MMIO_RD 0x00000026 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_MMIO_WRS 0x00000027 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_BAR 0x00000028 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_CC_WATCHDOG 0x0000002b +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_UNK12 0x0000002c +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC0_UNK13 0x0000002d +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1__MASK 0x00003f00 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1__SHIFT 8 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_GPC_UNK2 0x00000200 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_HUB_CHANNEL_SWITCH 0x00000300 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_HUB_UNK4 0x00000400 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_HUB_CTXCTL_DOWN 0x00000b00 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_HUB_UNK12 0x00000c00 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_ZERO 0x00002000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_STRAND 0x00002200 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_MMCTX 0x00002500 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_MMIO_RD 0x00002600 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_MMIO_WRS 0x00002700 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_BAR 0x00002800 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_CC_WATCHDOG 0x00002b00 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_UNK12 0x00002c00 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_SRC1_UNK13 0x00002d00 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_FUN__MASK 0x00010000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_FUN__SHIFT 16 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_FUN_OR 0x00000000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_FUN_AND 0x00010000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_NOT 0x00020000 +#define NVC0_PGRAPH_GPC_CTXCTL_INTR_ROUTE_LEVEL 0x00040000 + +#define NVC0_PGRAPH_GPC_CTXCTL_BAR_REQMASK(i0, i1) (0x0050240c + 0x8000*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_CTXCTL_BAR_REQMASK__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_BAR_REQMASK__LEN 0x00000002 + +#define NVC0_PGRAPH_GPC_CTXCTL_BAR(i0) (0x00502414 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_BAR_SET(i0) (0x00502418 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_CC_WATCHDOG(i0) (0x00502430 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_CC_WATCHDOG_TIME_REMAINING__MASK 0x3fffffff +#define NVC0_PGRAPH_GPC_CTXCTL_CC_WATCHDOG_TIME_REMAINING__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_CC_WATCHDOG_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_WRCMD_DATA(i0) (0x00502500 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_WRCMD_CMD(i0) (0x00502504 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_NEW_CAPS(i0) (0x00502620 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_NEW_CAPS_CODE_SIZE__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_CTXCTL_NEW_CAPS_CODE_SIZE__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_NEW_CAPS_CODE_SIZE__SHR 8 +#define NVC0_PGRAPH_GPC_CTXCTL_NEW_CAPS_DATA_SIZE__MASK 0x0000ff00 +#define NVC0_PGRAPH_GPC_CTXCTL_NEW_CAPS_DATA_SIZE__SHIFT 8 +#define NVC0_PGRAPH_GPC_CTXCTL_NEW_CAPS_DATA_SIZE__SHR 8 + +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_SAVE_SWBASE(i0) (0x00502700 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_SAVE_SWBASE__SHR 8 + +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_LOAD_SWBASE(i0) (0x00502704 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_LOAD_SWBASE__SHR 8 + +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_BASE(i0) (0x00502710 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL(i0) (0x00502714 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL_QFREE__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL_QFREE__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL_QLIMIT__MASK 0x00001f00 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL_QLIMIT__SHIFT 8 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL_DIR__MASK 0x00010000 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL_DIR__SHIFT 16 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL_DIR_SAVE 0x00000000 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL_DIR_LOAD 0x00010000 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL_START_TRIGGER 0x00020000 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_CTRL_STOP_TRIGGER 0x00040000 + +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_MULTI_STRIDE(i0) (0x00502718 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_MULTI_MASK(i0) (0x0050271c + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_QUEUE(i0) (0x00502720 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_QUEUE_BASE_EN 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_QUEUE_MULTI_EN 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_QUEUE_ADDR__MASK 0x03fffffc +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_QUEUE_ADDR__SHIFT 2 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_QUEUE_ADDR__SHR 2 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_QUEUE_CNTM1__MASK 0xfc000000 +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_QUEUE_CNTM1__SHIFT 26 + +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL(i0) (0x00502728 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL_UNK0 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL_ADDR__MASK 0x03fffffc +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL_ADDR__SHIFT 2 +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL_ADDR__SHR 2 +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL_WRS 0x20000000 +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL_ACCESS__MASK 0x40000000 +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL_ACCESS__SHIFT 30 +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL_ACCESS_READ 0x00000000 +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL_ACCESS_WRITE 0x40000000 +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_CTRL_TRIGGER 0x80000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_RDVAL(i0) (0x0050272c + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_MMIO_WRVAL(i0) (0x00502730 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_MMCTX_LOAD_COUNT(i0) (0x0050274c + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_CC_SCRATCH(i0, i1) (0x00502800 + 0x8000*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_CTXCTL_CC_SCRATCH__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_CC_SCRATCH__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_CTXCTL_CC_SCRATCH_SET(i0, i1) (0x00502820 + 0x8000*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_CTXCTL_CC_SCRATCH_SET__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_CC_SCRATCH_SET__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_CTXCTL_CC_SCRATCH_CLEAR(i0, i1) (0x00502840 + 0x8000*(i0) + 0x4*(i1)) +#define NVC0_PGRAPH_GPC_CTXCTL_CC_SCRATCH_CLEAR__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_CC_SCRATCH_CLEAR__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_CTXCTL_STRANDS(i0) (0x00502880 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_SAVE_SWBASE(i0) (0x00502908 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_SAVE_SWBASE__SHR 8 + +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_LOAD_SWBASE(i0) (0x0050290c + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_LOAD_SWBASE__SHR 8 + +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_SIZE(i0) (0x00502910 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_GENE_CNT(i0) (0x00502918 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_FIRST_GENE(i0) (0x0050291c + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_CMD(i0) (0x00502928 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_CMD_LATCH_FIRST_GENE 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_CMD_LATCH_GENE_CNT 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_CMD_SAVE 0x00000003 +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_CMD_LOAD 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_CMD_UNK5 0x00000005 +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_CMD_UNKA 0x0000000a +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_CMD_UNKB 0x0000000b +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_CMD_UNKC 0x0000000c +#define NVC0_PGRAPH_GPC_CTXCTL_STRAND_CMD_UNKD 0x0000000d + +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_BASE(i0) (0x00502a04 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_BASE__SHR 8 + +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CHAN(i0) (0x00502a0c + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CHAN_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CHAN_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CHAN_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CHAN_TARGET__MASK 0x30000000 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CHAN_TARGET__SHIFT 28 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CHAN_TARGET_VRAM 0x00000000 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CHAN_TARGET_SYSRAM 0x20000000 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CHAN_TARGET_SYSRAM_NO_SNOOP 0x30000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CMD(i0) (0x00502a10 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_CMD_LOAD_CHAN 0x00000007 + +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_TARGET(i0) (0x00502a20 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_TARGET_TARGET__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_TARGET_TARGET__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_TARGET_TARGET_VM 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_TARGET_TARGET_VRAM 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_TARGET_TARGET_SYSRAM_NOSNOOP 0x00000003 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_TARGET_TARGET_SYSRAM 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_MEM_TARGET_UNK31 0x80000000 + +#define NVC0_PGRAPH_GPC_CTXCTL_UNITS(i0) (0x00502608 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_UNITS_TP_COUNT__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_CTXCTL_UNITS_TP_COUNT__SHIFT 0 +#define NVC0_PGRAPH_GPC_CTXCTL_UNITS_UNK_ZCULL_COUNT__MASK 0x001f0000 +#define NVC0_PGRAPH_GPC_CTXCTL_UNITS_UNK_ZCULL_COUNT__SHIFT 16 + +#define NVC0_PGRAPH_GPC_CTXCTL_RED_SWITCH(i0) (0x00502614 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_RED_SWITCH_UNK0_GPC 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_RED_SWITCH_POWER_GPC 0x00000020 +#define NVC0_PGRAPH_GPC_CTXCTL_RED_SWITCH_ENABLE_GPC 0x00000200 +#define NVC0_PGRAPH_GPC_CTXCTL_RED_SWITCH_UNK11 0x00000800 + +#define NVC0_PGRAPH_GPC_CTXCTL_MYINDEX(i0) (0x00502618 + 0x8000*(i0)) + +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP(i0) (0x00502c90 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_PROP 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_ZCULL 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_CCACHE 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_ESETUP 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_TP__MASK 0x00ff0000 +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_TP__SHIFT 16 + +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_EN(i0) (0x00502c94 + 0x8000*(i0)) +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_EN_PROP 0x00000001 +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_EN_ZCULL 0x00000002 +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_EN_CCACHE 0x00000004 +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_EN_ESETUP 0x00000008 +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_EN_TP__MASK 0x00ff0000 +#define NVC0_PGRAPH_GPC_CTXCTL_TRAP_EN_TP__SHIFT 16 + +#define NVC0_PGRAPH_GPC_TP(i0, i1) (0x00504000 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP__ESIZE 0x00000800 +#define NVC0_PGRAPH_GPC_TP__LEN 0x00000004 + + +#define NVC0_PGRAPH_GPC_TP_POLY(i0, i1) (0x00504000 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_POLY__ESIZE 0x00000200 + +#define NVC0_PGRAPH_GPC_TP_POLY_POLY2ESETUP(i0, i1) (0x00504048 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_POLY_POLY2ESETUP_ADDRESS__MASK 0x0fffffff +#define NVC0_PGRAPH_GPC_TP_POLY_POLY2ESETUP_ADDRESS__SHIFT 0 +#define NVC0_PGRAPH_GPC_TP_POLY_POLY2ESETUP_ADDRESS__SHR 12 +#define NVC0_PGRAPH_GPC_TP_POLY_POLY2ESETUP_UNK28 0x10000000 + +#define NVC0_PGRAPH_GPC_TP_POLY_TRAP(i0, i1) (0x00504084 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_POLY_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_TP_POLY_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_TP_POLY_TPID(i0, i1) (0x00504088 + 0x8000*(i0) + 0x800*(i1)) + +#define NVC0_PGRAPH_GPC_TP_TEX(i0, i1) (0x00504200 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_TEX__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_TP_TEX_TRAP(i0, i1) (0x00504224 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_TEX_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_TP_TEX_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_TP_TPBUS(i0, i1) (0x00504300 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_TPBUS__ESIZE 0x00000100 + +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID(i0, i1, i2) (0x00504300 + 0x8000*(i0) + 0x800*(i1) + 0x4*(i2)) +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID__LEN 0x0000002c +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_0__MASK 0x0000001f +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_0__SHIFT 0 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_1__MASK 0x000003e0 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_1__SHIFT 5 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_2__MASK 0x00007c00 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_2__SHIFT 10 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_3__MASK 0x000f8000 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_3__SHIFT 15 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_4__MASK 0x01f00000 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_4__SHIFT 20 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_5__MASK 0x3e000000 +#define NVC0_PGRAPH_GPC_TP_TPBUS_TP_GPCID_5__SHIFT 25 + +#define NVC0_PGRAPH_GPC_TP_TPBUS_UNKD0(i0, i1) (0x005043d0 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_TPBUS_UNKD0_ROPC_COUNT__MASK 0x000000ff +#define NVC0_PGRAPH_GPC_TP_TPBUS_UNKD0_ROPC_COUNT__SHIFT 0 +#define NVC0_PGRAPH_GPC_TP_TPBUS_UNKD0_GPC_COUNT__MASK 0x0000ff00 +#define NVC0_PGRAPH_GPC_TP_TPBUS_UNKD0_GPC_COUNT__SHIFT 8 +#define NVC0_PGRAPH_GPC_TP_TPBUS_UNKD0_UNK16__MASK 0x1fff0000 +#define NVC0_PGRAPH_GPC_TP_TPBUS_UNKD0_UNK16__SHIFT 16 + +#define NVC0_PGRAPH_GPC_TP_TPBUS_UNKE4(i0, i1) (0x005043e4 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_TPBUS_UNKE4_UNK0__MASK 0x3fffffff +#define NVC0_PGRAPH_GPC_TP_TPBUS_UNKE4_UNK0__SHIFT 0 + +#define NVC0_PGRAPH_GPC_TP_L1(i0, i1) (0x00504480 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_L1__ESIZE 0x00000080 + +#define NVC0_PGRAPH_GPC_TP_L1_TRAP(i0, i1) (0x0050448c + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_L1_TRAP_GLOBAL_MAP_READ 0x00000002 +#define NVC0_PGRAPH_GPC_TP_L1_TRAP_GLOBAL_MAP_WRITE 0x00000004 +#define NVC0_PGRAPH_GPC_TP_L1_TRAP_CLEAR 0x40000000 +#define NVC0_PGRAPH_GPC_TP_L1_TRAP_ENABLE 0x80000000 + +#define NVC0_PGRAPH_GPC_TP_L1_TPID(i0, i1) (0x005044e8 + 0x8000*(i0) + 0x800*(i1)) + +#define NVC0_PGRAPH_GPC_TP_TRAP(i0, i1) (0x00504508 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_TRAP_TEX 0x00000001 +#define NVC0_PGRAPH_GPC_TP_TRAP_MP 0x00000002 +#define NVC0_PGRAPH_GPC_TP_TRAP_POLY 0x00000004 +#define NVC0_PGRAPH_GPC_TP_TRAP_L1C 0x00000008 + +#define NVC0_PGRAPH_GPC_TP_TRAP_EN(i0, i1) (0x0050450c + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_TRAP_EN_TEX 0x00000001 +#define NVC0_PGRAPH_GPC_TP_TRAP_EN_MP 0x00000002 +#define NVC0_PGRAPH_GPC_TP_TRAP_EN_POLY 0x00000004 +#define NVC0_PGRAPH_GPC_TP_TRAP_EN_L1C 0x00000008 + +#define NVC0_PGRAPH_GPC_TP_MP(i0, i1) (0x00504600 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_MP__ESIZE 0x00000200 + +#define NVC0_PGRAPH_GPC_TP_MP_UNK44_TRAP(i0, i1) (0x00504644 + 0x8000*(i0) + 0x800*(i1)) + +#define NVC0_PGRAPH_GPC_TP_MP_UNK4C_TRAP(i0, i1) (0x0050464c + 0x8000*(i0) + 0x800*(i1)) + +#define NVC0_PGRAPH_GPC_TP_MP_TRAP_HANDLER_PC(i0, i1) (0x00504658 + 0x8000*(i0) + 0x800*(i1)) + +#define NVC0_PGRAPH_GPC_TP_MP_PM_OP(i0, i1, i2) (0x00504660 + 0x8000*(i0) + 0x800*(i1) + 0x4*(i2)) +#define NVC0_PGRAPH_GPC_TP_MP_PM_OP__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_TP_MP_PM_OP__LEN 0x00000004 +#define NVC0_PGRAPH_GPC_TP_MP_PM_OP_0__MASK 0x0000ffff +#define NVC0_PGRAPH_GPC_TP_MP_PM_OP_0__SHIFT 0 +#define NVC0_PGRAPH_GPC_TP_MP_PM_OP_1__MASK 0xffff0000 +#define NVC0_PGRAPH_GPC_TP_MP_PM_OP_1__SHIFT 16 + +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER_OVERFLOW(i0, i1) (0x00504670 + 0x8000*(i0) + 0x800*(i1)) +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER_OVERFLOW_0 0x00000001 +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER_OVERFLOW_1 0x00000002 +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER_OVERFLOW_2 0x00000004 +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER_OVERFLOW_3 0x00000008 +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER_OVERFLOW_4 0x00000010 +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER_OVERFLOW_5 0x00000020 +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER_OVERFLOW_6 0x00000040 +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER_OVERFLOW_7 0x00000080 + +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER(i0, i1, i2) (0x00504674 + 0x8000*(i0) + 0x800*(i1) + 0x4*(i2)) +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER__ESIZE 0x00000004 +#define NVC0_PGRAPH_GPC_TP_MP_PM_COUNTER__LEN 0x00000008 + +#define NVC0_PGRAPH_GPC_TP_MP_TPID(i0, i1) (0x00504698 + 0x8000*(i0) + 0x800*(i1)) + + +#endif /* ___RNNDB____RNNDB_NVC0_PGRAPH_XML */ diff --git a/driver/pscnv/nvc0_vm.c b/driver/pscnv/nvc0_vm.c new file mode 100644 index 00000000..b5e72dea --- /dev/null +++ b/driver/pscnv/nvc0_vm.c @@ -0,0 +1,446 @@ +/* + * Copyright 2010 Christoph Bumiller. + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "nouveau_reg.h" +#include "pscnv_mem.h" +#include "pscnv_vm.h" +#include "pscnv_chan.h" +#include "nvc0_vm.h" +#include + +#define PSCNV_GEM_NOUSER 0x10 /* XXX */ + +int nvc0_vm_map_kernel(struct pscnv_bo *bo); +void nvc0_vm_takedown(struct drm_device *dev); +void nv84_vm_bar_flush(struct drm_device *dev); + +int +nvc0_tlb_flush(struct pscnv_vspace *vs) +{ + struct drm_device *dev = vs->dev; + uint32_t val; + + BUG_ON(!nvc0_vs(vs)->pd); + + NV_DEBUG(dev, "nvc0_tlb_flush 0x%010llx\n", nvc0_vs(vs)->pd->start); + + val = nv_rd32(dev, 0x100c80); + + nv_wr32(dev, 0x100cb8, nvc0_vs(vs)->pd->start >> 8); + nv_wr32(dev, 0x100cbc, 0x80000000 | ((vs->vid == -3) ? 0x5 : 0x1)); + + if (!nv_wait(dev, 0x100c80, ~0, val)) { + NV_ERROR(vs->dev, "tlb flush timed out\n"); + return -EBUSY; + } + return 0; +} + +static int +nvc0_vspace_fill_pde(struct pscnv_vspace *vs, struct nvc0_pgt *pgt) +{ + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + const uint32_t size = NVC0_VM_SPTE_COUNT << (3 - pgt->limit); + int i; + uint32_t pde[2]; + + pgt->bo[1] = pscnv_mem_alloc(vs->dev, size, PSCNV_GEM_CONTIG, 0, 0x59); + if (!pgt->bo[1]) + return -ENOMEM; + + for (i = 0; i < size; i += 4) + nv_wv32(pgt->bo[1], i, 0); + + pde[0] = pgt->limit << 2; + pde[1] = (pgt->bo[1]->start >> 8) | 1; + + if (vs->vid != -3) { + pgt->bo[0] = pscnv_mem_alloc(vs->dev, NVC0_VM_LPTE_COUNT * 8, + PSCNV_GEM_CONTIG, 0, 0x79); + if (!pgt->bo[0]) + return -ENOMEM; + + nvc0_vm_map_kernel(pgt->bo[0]); + nvc0_vm_map_kernel(pgt->bo[1]); + + for (i = 0; i < NVC0_VM_LPTE_COUNT * 8; i += 4) + nv_wv32(pgt->bo[0], i, 0); + + pde[0] |= (pgt->bo[0]->start >> 8) | 1; + } + dev_priv->vm->bar_flush(vs->dev); + + nv_wv32(nvc0_vs(vs)->pd, pgt->pde * 8 + 0, pde[0]); + nv_wv32(nvc0_vs(vs)->pd, pgt->pde * 8 + 4, pde[1]); + + dev_priv->vm->bar_flush(vs->dev); + return nvc0_tlb_flush(vs); +} + +static struct nvc0_pgt * +nvc0_vspace_pgt(struct pscnv_vspace *vs, unsigned int pde) +{ + struct nvc0_pgt *pt; + struct list_head *pts = &nvc0_vs(vs)->ptht[NVC0_PDE_HASH(pde)]; + + BUG_ON(pde >= NVC0_VM_PDE_COUNT); + + list_for_each_entry(pt, pts, head) + if (pt->pde == pde) + return pt; + + NV_DEBUG(vs->dev, "creating new page table: %i[%u]\n", vs->vid, pde); + + pt = kzalloc(sizeof *pt, GFP_KERNEL); + if (!pt) + return NULL; + pt->pde = pde; + pt->limit = 0; + + if (nvc0_vspace_fill_pde(vs, pt)) { + kfree(pt); + return NULL; + } + + list_add_tail(&pt->head, pts); + return pt; +} + +void +nvc0_pgt_del(struct pscnv_vspace *vs, struct nvc0_pgt *pgt) +{ + pscnv_vram_free(pgt->bo[1]); + if (pgt->bo[0]) + pscnv_vram_free(pgt->bo[0]); + list_del(&pgt->head); + + nv_wv32(nvc0_vs(vs)->pd, pgt->pde * 8 + 0, 0); + nv_wv32(nvc0_vs(vs)->pd, pgt->pde * 8 + 4, 0); + + kfree(pgt); +} + +int +nvc0_vspace_do_unmap(struct pscnv_vspace *vs, uint64_t offset, uint64_t size) +{ + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + uint32_t space; + + for (; size; offset += space) { + struct nvc0_pgt *pt; + int i, pte; + + pt = nvc0_vspace_pgt(vs, NVC0_PDE(offset)); + space = NVC0_VM_BLOCK_SIZE - (offset & NVC0_VM_BLOCK_MASK); + if (space > size) + space = size; + size -= space; + + pte = NVC0_SPTE(offset); + for (i = 0; i < (space >> NVC0_SPAGE_SHIFT) * 8; i += 4) + nv_wv32(pt->bo[1], pte * 8 + i, 0); + + if (!pt->bo[0]) + continue; + + pte = NVC0_LPTE(offset); + for (i = 0; i < (space >> NVC0_LPAGE_SHIFT) * 8; i += 4) + nv_wv32(pt->bo[0], pte * 8 + i, 0); + } + dev_priv->vm->bar_flush(vs->dev); + return nvc0_tlb_flush(vs); +} + +static inline void +write_pt(struct pscnv_bo *pt, int pte, int count, uint64_t phys, + int psz, uint32_t pfl0, uint32_t pfl1) +{ + int i; + uint32_t a = (phys >> 8) | pfl0; + uint32_t b = pfl1; + + psz >>= 8; + + for (i = pte * 8; i < (pte + count) * 8; i += 8, a += psz) { + nv_wv32(pt, i + 4, b); + nv_wv32(pt, i + 0, a); + } +} + +int +nvc0_vspace_place_map (struct pscnv_vspace *vs, struct pscnv_bo *bo, + uint64_t start, uint64_t end, int back, + struct pscnv_mm_node **res) +{ + int flags = 0; + + if ((bo->flags & PSCNV_GEM_MEMTYPE_MASK) == PSCNV_GEM_VRAM_LARGE) + flags = PSCNV_MM_LP; + if (back) + flags |= PSCNV_MM_FROMBACK; + + return pscnv_mm_alloc(vs->mm, bo->size, flags, start, end, res); +} + +int +nvc0_vspace_do_map(struct pscnv_vspace *vs, + struct pscnv_bo *bo, uint64_t offset) +{ + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + uint32_t pfl0, pfl1; + struct pscnv_mm_node *reg; + int i; + + pfl0 = 1; + if (vs->vid >= 0 && (bo->flags & PSCNV_GEM_NOUSER)) + pfl0 |= 2; + + pfl1 = bo->tile_flags << 4; + + switch (bo->flags & PSCNV_GEM_MEMTYPE_MASK) { + case PSCNV_GEM_SYSRAM_NOSNOOP: + pfl1 |= 0x2; + /* fall through */ + case PSCNV_GEM_SYSRAM_SNOOP: + { + unsigned int pde = NVC0_PDE(offset); + unsigned int pte = (offset & NVC0_VM_BLOCK_MASK) >> PAGE_SHIFT; + struct nvc0_pgt *pt = nvc0_vspace_pgt(vs, pde); + pfl1 |= 0x5; + for (i = 0; i < (bo->size >> PAGE_SHIFT); ++i) { + uint64_t phys = bo->dmapages[i]; + nv_wv32(pt->bo[1], pte * 8 + 4, pfl1); + nv_wv32(pt->bo[1], pte * 8 + 0, (phys >> 8) | pfl0); + pte++; + if ((pte & (NVC0_VM_BLOCK_MASK >> PAGE_SHIFT)) == 0) { + pte = 0; + pt = nvc0_vspace_pgt(vs, ++pde); + } + } + } + break; + case PSCNV_GEM_VRAM_SMALL: + case PSCNV_GEM_VRAM_LARGE: + for (reg = bo->mmnode; reg; reg = reg->next) { + uint32_t psh, psz; + uint64_t phys = reg->start, size = reg->size; + + int s = (bo->flags & PSCNV_GEM_MEMTYPE_MASK) != PSCNV_GEM_VRAM_LARGE; + if (vs->vid == -3) + s = 1; + psh = s ? NVC0_SPAGE_SHIFT : NVC0_LPAGE_SHIFT; + psz = 1 << psh; + + while (size) { + struct nvc0_pgt *pt; + int pte, count; + uint32_t space; + + space = NVC0_VM_BLOCK_SIZE - + (offset & NVC0_VM_BLOCK_MASK); + if (space > size) + space = size; + size -= space; + + pte = (offset & NVC0_VM_BLOCK_MASK) >> psh; + count = space >> psh; + pt = nvc0_vspace_pgt(vs, NVC0_PDE(offset)); + + write_pt(pt->bo[s], pte, count, phys, psz, pfl0, pfl1); + + offset += space; + phys += space; + } + } + break; + default: + return -ENOSYS; + } + dev_priv->vm->bar_flush(vs->dev); + return nvc0_tlb_flush(vs); +} + +int nvc0_vspace_new(struct pscnv_vspace *vs) { + int i, ret; + + if (vs->size > 1ull << 40) + return -EINVAL; + + vs->engdata = kzalloc(sizeof(struct nvc0_vspace), GFP_KERNEL); + if (!vs->engdata) { + NV_ERROR(vs->dev, "VM: Couldn't alloc vspace eng\n"); + return -ENOMEM; + } + + nvc0_vs(vs)->pd = pscnv_mem_alloc(vs->dev, NVC0_VM_PDE_COUNT * 8, + PSCNV_GEM_CONTIG, 0, 0xdeadcafe); + if (!nvc0_vs(vs)->pd) { + kfree(vs->engdata); + return -ENOMEM; + } + + if (vs->vid != -3) + nvc0_vm_map_kernel(nvc0_vs(vs)->pd); + + for (i = 0; i < NVC0_VM_PDE_COUNT; i++) { + nv_wv32(nvc0_vs(vs)->pd, i * 8, 0); + nv_wv32(nvc0_vs(vs)->pd, i * 8 + 4, 0); + } + + for (i = 0; i < NVC0_PDE_HT_SIZE; ++i) + INIT_LIST_HEAD(&nvc0_vs(vs)->ptht[i]); + + ret = pscnv_mm_init(vs->dev, 0, vs->size, 0x1000, 0x20000, 1, &vs->mm); + if (ret) { + pscnv_mem_free(nvc0_vs(vs)->pd); + kfree(vs->engdata); + } + return ret; +} + +void nvc0_vspace_free(struct pscnv_vspace *vs) { + int i; + for (i = 0; i < NVC0_PDE_HT_SIZE; i++) { + struct nvc0_pgt *pgt, *save; + list_for_each_entry_safe(pgt, save, &nvc0_vs(vs)->ptht[i], head) + nvc0_pgt_del(vs, pgt); + } + pscnv_mem_free(nvc0_vs(vs)->pd); + + kfree(vs->engdata); +} + +int nvc0_vm_map_user(struct pscnv_bo *bo) { + struct drm_nouveau_private *dev_priv = bo->dev->dev_private; + struct nvc0_vm_engine *vme = nvc0_vm(dev_priv->vm); + if (bo->map1) + return 0; + return pscnv_vspace_map(vme->bar1vm, bo, 0, dev_priv->fb_size, 0, &bo->map1); +} + +int nvc0_vm_map_kernel(struct pscnv_bo *bo) { + struct drm_nouveau_private *dev_priv = bo->dev->dev_private; + struct nvc0_vm_engine *vme = nvc0_vm(dev_priv->vm); + if (bo->map3) + return 0; + return pscnv_vspace_map(vme->bar3vm, bo, 0, dev_priv->ramin_size, 0, &bo->map3); +} + +int +nvc0_vm_init(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_pgt *pt; + struct nvc0_vm_engine *vme = kzalloc(sizeof *vme, GFP_KERNEL); + if (!vme) { + NV_ERROR(dev, "VM: Couldn't alloc engine\n"); + return -ENOMEM; + } + vme->base.takedown = nvc0_vm_takedown; + vme->base.do_vspace_new = nvc0_vspace_new; + vme->base.do_vspace_free = nvc0_vspace_free; + vme->base.place_map = nvc0_vspace_place_map; + vme->base.do_map = nvc0_vspace_do_map; + vme->base.do_unmap = nvc0_vspace_do_unmap; + vme->base.map_user = nvc0_vm_map_user; + vme->base.map_kernel = nvc0_vm_map_kernel; + vme->base.bar_flush = nv84_vm_bar_flush; + dev_priv->vm = &vme->base; + + dev_priv->vm_ramin_base = 0; + spin_lock_init(&dev_priv->vm->vs_lock); + + nv_wr32(dev, 0x200, 0xfffffeff); + nv_wr32(dev, 0x200, 0xffffffff); + + nv_wr32(dev, 0x100c80, 0x00208000); + + vme->bar3vm = pscnv_vspace_new (dev, dev_priv->ramin_size, 0, 3); + if (!vme->bar3vm) { + kfree(vme); + dev_priv->vm = 0; + return -ENOMEM; + } + vme->bar3ch = pscnv_chan_new (dev, vme->bar3vm, 3); + if (!vme->bar3ch) { + pscnv_vspace_unref(vme->bar3vm); + kfree(vme); + dev_priv->vm = 0; + return -ENOMEM; + } + nv_wr32(dev, 0x1714, 0xc0000000 | vme->bar3ch->bo->start >> 12); + + dev_priv->vm_ok = 1; + + nvc0_vm_map_kernel(vme->bar3ch->bo); + nvc0_vm_map_kernel(nvc0_vs(vme->bar3vm)->pd); + pt = nvc0_vspace_pgt(vme->bar3vm, 0); + if (!pt) { + NV_ERROR(dev, "VM: failed to allocate RAMIN page table\n"); + return -ENOMEM; + } + nvc0_vm_map_kernel(pt->bo[1]); + + vme->bar1vm = pscnv_vspace_new (dev, dev_priv->fb_size, 0, 1); + if (!vme->bar1vm) { + dev_priv->vm_ok = 0; + pscnv_chan_unref(vme->bar3ch); + pscnv_vspace_unref(vme->bar3vm); + kfree(vme); + dev_priv->vm = 0; + return -ENOMEM; + } + vme->bar1ch = pscnv_chan_new (dev, vme->bar1vm, 1); + if (!vme->bar1ch) { + dev_priv->vm_ok = 0; + pscnv_vspace_unref(vme->bar1vm); + pscnv_chan_unref(vme->bar3ch); + pscnv_vspace_unref(vme->bar3vm); + kfree(vme); + dev_priv->vm = 0; + return -ENOMEM; + } + nv_wr32(dev, 0x1704, 0x80000000 | vme->bar1ch->bo->start >> 12); + return 0; +} + +void +nvc0_vm_takedown(struct drm_device *dev) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct nvc0_vm_engine *vme = nvc0_vm(dev_priv->vm); + /* XXX: write me. */ + dev_priv->vm_ok = 0; + nv_wr32(dev, 0x1704, 0); + nv_wr32(dev, 0x1714, 0); + nv_wr32(dev, 0x1718, 0); + pscnv_chan_unref(vme->bar1ch); + pscnv_vspace_unref(vme->bar1vm); + pscnv_chan_unref(vme->bar3ch); + pscnv_vspace_unref(vme->bar3vm); + kfree(vme); + dev_priv->vm = 0; +} + diff --git a/driver/pscnv/nvc0_vm.h b/driver/pscnv/nvc0_vm.h new file mode 100644 index 00000000..3ca8e16e --- /dev/null +++ b/driver/pscnv/nvc0_vm.h @@ -0,0 +1,57 @@ +#ifndef __NVC0_VM_H__ +#define __NVC0_VM_H__ + +#include "drmP.h" +#include "drm.h" +#include "pscnv_engine.h" + +#define NVC0_VM_SIZE 0x10000000000ULL + +#define NVC0_SPAGE_SHIFT 12 +#define NVC0_LPAGE_SHIFT 17 +#define NVC0_SPAGE_MASK 0x00fff +#define NVC0_LPAGE_MASK 0x1ffff + +#define NVC0_VM_PDE_COUNT 0x2000 +#define NVC0_VM_BLOCK_SIZE 0x8000000 +#define NVC0_VM_BLOCK_MASK 0x7ffffff +#define NVC0_VM_SPTE_COUNT (NVC0_VM_BLOCK_SIZE >> NVC0_SPAGE_SHIFT) +#define NVC0_VM_LPTE_COUNT (NVC0_VM_BLOCK_SIZE >> NVC0_LPAGE_SHIFT) + +#define NVC0_PDE(a) ((a) / NVC0_VM_BLOCK_SIZE) +#define NVC0_SPTE(a) (((a) & NVC0_VM_BLOCK_MASK) >> NVC0_SPAGE_SHIFT) +#define NVC0_LPTE(a) (((a) & NVC0_VM_BLOCK_MASK) >> NVC0_LPAGE_SHIFT) + +#define NVC0_PDE_HT_SIZE 32 +#define NVC0_PDE_HASH(n) (n % NVC0_PDE_HT_SIZE) + +#define nvc0_vm(x) container_of(x, struct nvc0_vm_engine, base) +#define nvc0_vs(x) ((struct nvc0_vspace *)(x)->engdata) + +struct nvc0_pgt { + struct list_head head; + unsigned int pde; + unsigned int limit; /* virtual range = NVC0_VM_BLOCK_SIZE >> limit */ + struct pscnv_bo *bo[2]; /* 128 KiB and 4 KiB page tables */ +}; + +struct nvc0_vm_engine { + struct pscnv_vm_engine base; + struct pscnv_vspace *bar1vm; + struct pscnv_chan *bar1ch; + struct pscnv_vspace *bar3vm; + struct pscnv_chan *bar3ch; +}; + +struct nvc0_vspace { + struct pscnv_bo *pd; + struct list_head ptht[NVC0_PDE_HT_SIZE]; + struct pscnv_mm_node *obj19848; + struct pscnv_mm_node *obj08004; + struct pscnv_mm_node *obj0800c; + struct pscnv_bo *mmio_bo; + struct pscnv_mm_node *mmio_vm; + uint32_t mmio_count; +}; + +#endif /* __NVC0_VM_H__ */ diff --git a/driver/pscnv/nvc0_vram.c b/driver/pscnv/nvc0_vram.c new file mode 100644 index 00000000..bde59f2b --- /dev/null +++ b/driver/pscnv/nvc0_vram.c @@ -0,0 +1,115 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "pscnv_mem.h" + +#define NVC0_MEM_CTRLR_COUNT 0x00121c74 +#define NVC0_MEM_CTRLR_RAM_AMOUNT 0x0010f20c + +int nvc0_vram_alloc(struct pscnv_bo *bo); +int nvc0_sysram_tiling_ok(struct pscnv_bo *bo); + +int +nvc0_vram_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int ret; + uint32_t ctrlr_num, ctrlr_amt; + + dev_priv->vram = kzalloc (sizeof *dev_priv->vram, GFP_KERNEL); + if (!dev_priv->vram) { + NV_ERROR(dev, "VRAM: out ot memory\n"); + return -ENOMEM; + } + + dev_priv->vram->alloc = nvc0_vram_alloc; + dev_priv->vram->free = pscnv_vram_free; + dev_priv->vram->takedown = pscnv_vram_takedown; + dev_priv->vram->sysram_tiling_ok = nvc0_sysram_tiling_ok; + + ctrlr_num = nv_rd32(dev, NVC0_MEM_CTRLR_COUNT); + ctrlr_amt = nv_rd32(dev, NVC0_MEM_CTRLR_RAM_AMOUNT); + + dev_priv->vram_size = ctrlr_num * (ctrlr_amt << 20); + + if (!dev_priv->vram_size) { + NV_ERROR(dev, "No VRAM detected, aborting.\n"); + return -ENODEV; + } + + NV_INFO(dev, "VRAM: size 0x%llx, %d controllers\n", + dev_priv->vram_size, ctrlr_num); + + ret = pscnv_mm_init(dev, 0x40000, dev_priv->vram_size - 0x20000, 0x1000, 0x20000, 0x1000, &dev_priv->vram_mm); + if (ret) { + kfree(dev_priv->vram); + return ret; + } + + return 0; +} + +int +nvc0_sysram_tiling_ok(struct pscnv_bo *bo) { + switch (bo->tile_flags) { + case 0: + case 0xdb: + case 0xfe: + return 1; + default: + return 0; + } +} + +int +nvc0_vram_alloc(struct pscnv_bo *bo) +{ + struct drm_device *dev = bo->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + int flags, ret; + if (bo->tile_flags & 0xffffff00) + return -EINVAL; + flags = 0; + bo->size = roundup(bo->size, 0x1000); + if ((bo->flags & PSCNV_GEM_MEMTYPE_MASK) == PSCNV_GEM_VRAM_LARGE) { + flags |= PSCNV_MM_LP; + bo->size = roundup(bo->size, 0x20000); + } + if (!(bo->flags & PSCNV_GEM_CONTIG)) + flags |= PSCNV_MM_FRAGOK; + mutex_lock(&dev_priv->vram_mutex); + ret = pscnv_mm_alloc(dev_priv->vram_mm, bo->size, flags, 0, dev_priv->vram_size, &bo->mmnode); + if (!ret) { + if (bo->flags & PSCNV_GEM_CONTIG) + bo->start = bo->mmnode->start; + bo->mmnode->tag = bo; + } + mutex_unlock(&dev_priv->vram_mutex); + return ret; +} diff --git a/driver/pscnv/nvreg.h b/driver/pscnv/nvreg.h new file mode 100644 index 00000000..d18e8371 --- /dev/null +++ b/driver/pscnv/nvreg.h @@ -0,0 +1,536 @@ +/* $XConsortium: nvreg.h /main/2 1996/10/28 05:13:41 kaleb $ */ +/* + * Copyright 1996-1997 David J. McKay + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * DAVID J. MCKAY BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF + * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/nv/nvreg.h,v 1.6 2002/01/25 21:56:06 tsi Exp $ */ + +#ifndef __NVREG_H_ +#define __NVREG_H_ + +#define NV_PMC_OFFSET 0x00000000 +#define NV_PMC_SIZE 0x00001000 + +#define NV_PBUS_OFFSET 0x00001000 +#define NV_PBUS_SIZE 0x00001000 + +#define NV_PFIFO_OFFSET 0x00002000 +#define NV_PFIFO_SIZE 0x00002000 + +#define NV_HDIAG_OFFSET 0x00005000 +#define NV_HDIAG_SIZE 0x00001000 + +#define NV_PRAM_OFFSET 0x00006000 +#define NV_PRAM_SIZE 0x00001000 + +#define NV_PVIDEO_OFFSET 0x00008000 +#define NV_PVIDEO_SIZE 0x00001000 + +#define NV_PTIMER_OFFSET 0x00009000 +#define NV_PTIMER_SIZE 0x00001000 + +#define NV_PPM_OFFSET 0x0000A000 +#define NV_PPM_SIZE 0x00001000 + +#define NV_PTV_OFFSET 0x0000D000 +#define NV_PTV_SIZE 0x00001000 + +#define NV_PRMVGA_OFFSET 0x000A0000 +#define NV_PRMVGA_SIZE 0x00020000 + +#define NV_PRMVIO0_OFFSET 0x000C0000 +#define NV_PRMVIO_SIZE 0x00002000 +#define NV_PRMVIO1_OFFSET 0x000C2000 + +#define NV_PFB_OFFSET 0x00100000 +#define NV_PFB_SIZE 0x00001000 + +#define NV_PEXTDEV_OFFSET 0x00101000 +#define NV_PEXTDEV_SIZE 0x00001000 + +#define NV_PME_OFFSET 0x00200000 +#define NV_PME_SIZE 0x00001000 + +#define NV_PROM_OFFSET 0x00300000 +#define NV_PROM_SIZE 0x00010000 + +#define NV_PGRAPH_OFFSET 0x00400000 +#define NV_PGRAPH_SIZE 0x00010000 + +#define NV_PCRTC0_OFFSET 0x00600000 +#define NV_PCRTC0_SIZE 0x00002000 /* empirical */ + +#define NV_PRMCIO0_OFFSET 0x00601000 +#define NV_PRMCIO_SIZE 0x00002000 +#define NV_PRMCIO1_OFFSET 0x00603000 + +#define NV50_DISPLAY_OFFSET 0x00610000 +#define NV50_DISPLAY_SIZE 0x0000FFFF + +#define NV_PRAMDAC0_OFFSET 0x00680000 +#define NV_PRAMDAC0_SIZE 0x00002000 + +#define NV_PRMDIO0_OFFSET 0x00681000 +#define NV_PRMDIO_SIZE 0x00002000 +#define NV_PRMDIO1_OFFSET 0x00683000 + +#define NV_PRAMIN_OFFSET 0x00700000 +#define NV_PRAMIN_SIZE 0x00100000 + +#define NV_FIFO_OFFSET 0x00800000 +#define NV_FIFO_SIZE 0x00800000 + +#define NV_PMC_BOOT_0 0x00000000 +#define NV_PMC_ENABLE 0x00000200 + +#define NV_VIO_VSE2 0x000003c3 +#define NV_VIO_SRX 0x000003c4 + +#define NV_CIO_CRX__COLOR 0x000003d4 +#define NV_CIO_CR__COLOR 0x000003d5 + +#define NV_PBUS_DEBUG_1 0x00001084 +#define NV_PBUS_DEBUG_4 0x00001098 +#define NV_PBUS_DEBUG_DUALHEAD_CTL 0x000010f0 +#define NV_PBUS_POWERCTRL_1 0x00001584 +#define NV_PBUS_POWERCTRL_2 0x00001588 +#define NV_PBUS_POWERCTRL_4 0x00001590 +#define NV_PBUS_PCI_NV_19 0x0000184C +#define NV_PBUS_PCI_NV_20 0x00001850 +# define NV_PBUS_PCI_NV_20_ROM_SHADOW_DISABLED (0 << 0) +# define NV_PBUS_PCI_NV_20_ROM_SHADOW_ENABLED (1 << 0) + +#define NV_PFIFO_RAMHT 0x00002210 + +#define NV_PTV_TV_INDEX 0x0000d220 +#define NV_PTV_TV_DATA 0x0000d224 +#define NV_PTV_HFILTER 0x0000d310 +#define NV_PTV_HFILTER2 0x0000d390 +#define NV_PTV_VFILTER 0x0000d510 + +#define NV_PRMVIO_MISC__WRITE 0x000c03c2 +#define NV_PRMVIO_SRX 0x000c03c4 +#define NV_PRMVIO_SR 0x000c03c5 +# define NV_VIO_SR_RESET_INDEX 0x00 +# define NV_VIO_SR_CLOCK_INDEX 0x01 +# define NV_VIO_SR_PLANE_MASK_INDEX 0x02 +# define NV_VIO_SR_CHAR_MAP_INDEX 0x03 +# define NV_VIO_SR_MEM_MODE_INDEX 0x04 +#define NV_PRMVIO_MISC__READ 0x000c03cc +#define NV_PRMVIO_GRX 0x000c03ce +#define NV_PRMVIO_GX 0x000c03cf +# define NV_VIO_GX_SR_INDEX 0x00 +# define NV_VIO_GX_SREN_INDEX 0x01 +# define NV_VIO_GX_CCOMP_INDEX 0x02 +# define NV_VIO_GX_ROP_INDEX 0x03 +# define NV_VIO_GX_READ_MAP_INDEX 0x04 +# define NV_VIO_GX_MODE_INDEX 0x05 +# define NV_VIO_GX_MISC_INDEX 0x06 +# define NV_VIO_GX_DONT_CARE_INDEX 0x07 +# define NV_VIO_GX_BIT_MASK_INDEX 0x08 + +#define NV_PFB_BOOT_0 0x00100000 +#define NV_PFB_CFG0 0x00100200 +#define NV_PFB_CFG1 0x00100204 +#define NV_PFB_CSTATUS 0x0010020C +#define NV_PFB_REFCTRL 0x00100210 +# define NV_PFB_REFCTRL_VALID_1 (1 << 31) +#define NV_PFB_PAD 0x0010021C +# define NV_PFB_PAD_CKE_NORMAL (1 << 0) +#define NV_PFB_TILE_NV10 0x00100240 +#define NV_PFB_TILE_SIZE_NV10 0x00100244 +#define NV_PFB_REF 0x001002D0 +# define NV_PFB_REF_CMD_REFRESH (1 << 0) +#define NV_PFB_PRE 0x001002D4 +# define NV_PFB_PRE_CMD_PRECHARGE (1 << 0) +#define NV_PFB_CLOSE_PAGE2 0x0010033C +#define NV_PFB_TILE_NV40 0x00100600 +#define NV_PFB_TILE_SIZE_NV40 0x00100604 + +#define NV_PEXTDEV_BOOT_0 0x00101000 +# define NV_PEXTDEV_BOOT_0_STRAP_FP_IFACE_12BIT (8 << 12) +#define NV_PEXTDEV_BOOT_3 0x0010100c + +#define NV_PCRTC_INTR_0 0x00600100 +# define NV_PCRTC_INTR_0_VBLANK (1 << 0) +#define NV_PCRTC_INTR_EN_0 0x00600140 +#define NV_PCRTC_START 0x00600800 +#define NV_PCRTC_CONFIG 0x00600804 +# define NV_PCRTC_CONFIG_START_ADDRESS_NON_VGA (1 << 0) +# define NV_PCRTC_CONFIG_START_ADDRESS_HSYNC (2 << 0) +#define NV_PCRTC_CURSOR_CONFIG 0x00600810 +# define NV_PCRTC_CURSOR_CONFIG_ENABLE_ENABLE (1 << 0) +# define NV_PCRTC_CURSOR_CONFIG_DOUBLE_SCAN_ENABLE (1 << 4) +# define NV_PCRTC_CURSOR_CONFIG_ADDRESS_SPACE_PNVM (1 << 8) +# define NV_PCRTC_CURSOR_CONFIG_CUR_BPP_32 (1 << 12) +# define NV_PCRTC_CURSOR_CONFIG_CUR_PIXELS_64 (1 << 16) +# define NV_PCRTC_CURSOR_CONFIG_CUR_LINES_32 (2 << 24) +# define NV_PCRTC_CURSOR_CONFIG_CUR_LINES_64 (4 << 24) +# define NV_PCRTC_CURSOR_CONFIG_CUR_BLEND_ALPHA (1 << 28) + +/* note: PCRTC_GPIO is not available on nv10, and in fact aliases 0x600810 */ +#define NV_PCRTC_GPIO 0x00600818 +#define NV_PCRTC_GPIO_EXT 0x0060081c +#define NV_PCRTC_830 0x00600830 +#define NV_PCRTC_834 0x00600834 +#define NV_PCRTC_850 0x00600850 +#define NV_PCRTC_ENGINE_CTRL 0x00600860 +# define NV_CRTC_FSEL_I2C (1 << 4) +# define NV_CRTC_FSEL_OVERLAY (1 << 12) + +#define NV_PRMCIO_ARX 0x006013c0 +#define NV_PRMCIO_AR__WRITE 0x006013c0 +#define NV_PRMCIO_AR__READ 0x006013c1 +# define NV_CIO_AR_MODE_INDEX 0x10 +# define NV_CIO_AR_OSCAN_INDEX 0x11 +# define NV_CIO_AR_PLANE_INDEX 0x12 +# define NV_CIO_AR_HPP_INDEX 0x13 +# define NV_CIO_AR_CSEL_INDEX 0x14 +#define NV_PRMCIO_INP0 0x006013c2 +#define NV_PRMCIO_CRX__COLOR 0x006013d4 +#define NV_PRMCIO_CR__COLOR 0x006013d5 + /* Standard VGA CRTC registers */ +# define NV_CIO_CR_HDT_INDEX 0x00 /* horizontal display total */ +# define NV_CIO_CR_HDE_INDEX 0x01 /* horizontal display end */ +# define NV_CIO_CR_HBS_INDEX 0x02 /* horizontal blanking start */ +# define NV_CIO_CR_HBE_INDEX 0x03 /* horizontal blanking end */ +# define NV_CIO_CR_HBE_4_0 4:0 +# define NV_CIO_CR_HRS_INDEX 0x04 /* horizontal retrace start */ +# define NV_CIO_CR_HRE_INDEX 0x05 /* horizontal retrace end */ +# define NV_CIO_CR_HRE_4_0 4:0 +# define NV_CIO_CR_HRE_HBE_5 7:7 +# define NV_CIO_CR_VDT_INDEX 0x06 /* vertical display total */ +# define NV_CIO_CR_OVL_INDEX 0x07 /* overflow bits */ +# define NV_CIO_CR_OVL_VDT_8 0:0 +# define NV_CIO_CR_OVL_VDE_8 1:1 +# define NV_CIO_CR_OVL_VRS_8 2:2 +# define NV_CIO_CR_OVL_VBS_8 3:3 +# define NV_CIO_CR_OVL_VDT_9 5:5 +# define NV_CIO_CR_OVL_VDE_9 6:6 +# define NV_CIO_CR_OVL_VRS_9 7:7 +# define NV_CIO_CR_RSAL_INDEX 0x08 /* normally "preset row scan" */ +# define NV_CIO_CR_CELL_HT_INDEX 0x09 /* cell height?! normally "max scan line" */ +# define NV_CIO_CR_CELL_HT_VBS_9 5:5 +# define NV_CIO_CR_CELL_HT_SCANDBL 7:7 +# define NV_CIO_CR_CURS_ST_INDEX 0x0a /* cursor start */ +# define NV_CIO_CR_CURS_END_INDEX 0x0b /* cursor end */ +# define NV_CIO_CR_SA_HI_INDEX 0x0c /* screen start address high */ +# define NV_CIO_CR_SA_LO_INDEX 0x0d /* screen start address low */ +# define NV_CIO_CR_TCOFF_HI_INDEX 0x0e /* cursor offset high */ +# define NV_CIO_CR_TCOFF_LO_INDEX 0x0f /* cursor offset low */ +# define NV_CIO_CR_VRS_INDEX 0x10 /* vertical retrace start */ +# define NV_CIO_CR_VRE_INDEX 0x11 /* vertical retrace end */ +# define NV_CIO_CR_VRE_3_0 3:0 +# define NV_CIO_CR_VDE_INDEX 0x12 /* vertical display end */ +# define NV_CIO_CR_OFFSET_INDEX 0x13 /* sets screen pitch */ +# define NV_CIO_CR_ULINE_INDEX 0x14 /* underline location */ +# define NV_CIO_CR_VBS_INDEX 0x15 /* vertical blank start */ +# define NV_CIO_CR_VBE_INDEX 0x16 /* vertical blank end */ +# define NV_CIO_CR_MODE_INDEX 0x17 /* crtc mode control */ +# define NV_CIO_CR_LCOMP_INDEX 0x18 /* line compare */ + /* Extended VGA CRTC registers */ +# define NV_CIO_CRE_RPC0_INDEX 0x19 /* repaint control 0 */ +# define NV_CIO_CRE_RPC0_OFFSET_10_8 7:5 +# define NV_CIO_CRE_RPC1_INDEX 0x1a /* repaint control 1 */ +# define NV_CIO_CRE_RPC1_LARGE 2:2 +# define NV_CIO_CRE_FF_INDEX 0x1b /* fifo control */ +# define NV_CIO_CRE_ENH_INDEX 0x1c /* enhanced? */ +# define NV_CIO_SR_LOCK_INDEX 0x1f /* crtc lock */ +# define NV_CIO_SR_UNLOCK_RW_VALUE 0x57 +# define NV_CIO_SR_LOCK_VALUE 0x99 +# define NV_CIO_CRE_FFLWM__INDEX 0x20 /* fifo low water mark */ +# define NV_CIO_CRE_21 0x21 /* vga shadow crtc lock */ +# define NV_CIO_CRE_LSR_INDEX 0x25 /* ? */ +# define NV_CIO_CRE_LSR_VDT_10 0:0 +# define NV_CIO_CRE_LSR_VDE_10 1:1 +# define NV_CIO_CRE_LSR_VRS_10 2:2 +# define NV_CIO_CRE_LSR_VBS_10 3:3 +# define NV_CIO_CRE_LSR_HBE_6 4:4 +# define NV_CIO_CR_ARX_INDEX 0x26 /* attribute index -- ro copy of 0x60.3c0 */ +# define NV_CIO_CRE_CHIP_ID_INDEX 0x27 /* chip revision */ +# define NV_CIO_CRE_PIXEL_INDEX 0x28 +# define NV_CIO_CRE_PIXEL_FORMAT 1:0 +# define NV_CIO_CRE_HEB__INDEX 0x2d /* horizontal extra bits? */ +# define NV_CIO_CRE_HEB_HDT_8 0:0 +# define NV_CIO_CRE_HEB_HDE_8 1:1 +# define NV_CIO_CRE_HEB_HBS_8 2:2 +# define NV_CIO_CRE_HEB_HRS_8 3:3 +# define NV_CIO_CRE_HEB_ILC_8 4:4 +# define NV_CIO_CRE_2E 0x2e /* some scratch or dummy reg to force writes to sink in */ +# define NV_CIO_CRE_HCUR_ADDR2_INDEX 0x2f /* cursor */ +# define NV_CIO_CRE_HCUR_ADDR0_INDEX 0x30 /* pixmap */ +# define NV_CIO_CRE_HCUR_ADDR0_ADR 6:0 +# define NV_CIO_CRE_HCUR_ASI 7:7 +# define NV_CIO_CRE_HCUR_ADDR1_INDEX 0x31 /* address */ +# define NV_CIO_CRE_HCUR_ADDR1_ENABLE 0:0 +# define NV_CIO_CRE_HCUR_ADDR1_CUR_DBL 1:1 +# define NV_CIO_CRE_HCUR_ADDR1_ADR 7:2 +# define NV_CIO_CRE_LCD__INDEX 0x33 +# define NV_CIO_CRE_LCD_LCD_SELECT 0:0 +# define NV_CIO_CRE_LCD_ROUTE_MASK 0x3b +# define NV_CIO_CRE_DDC0_STATUS__INDEX 0x36 +# define NV_CIO_CRE_DDC0_WR__INDEX 0x37 +# define NV_CIO_CRE_ILACE__INDEX 0x39 /* interlace */ +# define NV_CIO_CRE_SCRATCH3__INDEX 0x3b +# define NV_CIO_CRE_SCRATCH4__INDEX 0x3c +# define NV_CIO_CRE_DDC_STATUS__INDEX 0x3e +# define NV_CIO_CRE_DDC_WR__INDEX 0x3f +# define NV_CIO_CRE_EBR_INDEX 0x41 /* extra bits ? (vertical) */ +# define NV_CIO_CRE_EBR_VDT_11 0:0 +# define NV_CIO_CRE_EBR_VDE_11 2:2 +# define NV_CIO_CRE_EBR_VRS_11 4:4 +# define NV_CIO_CRE_EBR_VBS_11 6:6 +# define NV_CIO_CRE_43 0x43 +# define NV_CIO_CRE_44 0x44 /* head control */ +# define NV_CIO_CRE_CSB 0x45 /* colour saturation boost */ +# define NV_CIO_CRE_RCR 0x46 +# define NV_CIO_CRE_RCR_ENDIAN_BIG 7:7 +# define NV_CIO_CRE_47 0x47 /* extended fifo lwm, used on nv30+ */ +# define NV_CIO_CRE_49 0x49 +# define NV_CIO_CRE_4B 0x4b /* given patterns in 0x[2-3][a-c] regs, probably scratch 6 */ +# define NV_CIO_CRE_TVOUT_LATENCY 0x52 +# define NV_CIO_CRE_53 0x53 /* `fp_htiming' according to Haiku */ +# define NV_CIO_CRE_54 0x54 /* `fp_vtiming' according to Haiku */ +# define NV_CIO_CRE_57 0x57 /* index reg for cr58 */ +# define NV_CIO_CRE_58 0x58 /* data reg for cr57 */ +# define NV_CIO_CRE_59 0x59 /* related to on/off-chip-ness of digital outputs */ +# define NV_CIO_CRE_5B 0x5B /* newer colour saturation reg */ +# define NV_CIO_CRE_85 0x85 +# define NV_CIO_CRE_86 0x86 +#define NV_PRMCIO_INP0__COLOR 0x006013da + +#define NV_PRAMDAC_CU_START_POS 0x00680300 +# define NV_PRAMDAC_CU_START_POS_X 15:0 +# define NV_PRAMDAC_CU_START_POS_Y 31:16 +#define NV_RAMDAC_NV10_CURSYNC 0x00680404 + +#define NV_PRAMDAC_NVPLL_COEFF 0x00680500 +#define NV_PRAMDAC_MPLL_COEFF 0x00680504 +#define NV_PRAMDAC_VPLL_COEFF 0x00680508 +# define NV30_RAMDAC_ENABLE_VCO2 (8 << 4) + +#define NV_PRAMDAC_PLL_COEFF_SELECT 0x0068050c +# define NV_PRAMDAC_PLL_COEFF_SELECT_USE_VPLL2_TRUE (4 << 0) +# define NV_PRAMDAC_PLL_COEFF_SELECT_SOURCE_PROG_MPLL (1 << 8) +# define NV_PRAMDAC_PLL_COEFF_SELECT_SOURCE_PROG_VPLL (2 << 8) +# define NV_PRAMDAC_PLL_COEFF_SELECT_SOURCE_PROG_NVPLL (4 << 8) +# define NV_PRAMDAC_PLL_COEFF_SELECT_PLL_SOURCE_VPLL2 (8 << 8) +# define NV_PRAMDAC_PLL_COEFF_SELECT_TV_VSCLK1 (1 << 16) +# define NV_PRAMDAC_PLL_COEFF_SELECT_TV_PCLK1 (2 << 16) +# define NV_PRAMDAC_PLL_COEFF_SELECT_TV_VSCLK2 (4 << 16) +# define NV_PRAMDAC_PLL_COEFF_SELECT_TV_PCLK2 (8 << 16) +# define NV_PRAMDAC_PLL_COEFF_SELECT_TV_CLK_SOURCE_VIP (1 << 20) +# define NV_PRAMDAC_PLL_COEFF_SELECT_VCLK_RATIO_DB2 (1 << 28) +# define NV_PRAMDAC_PLL_COEFF_SELECT_VCLK2_RATIO_DB2 (2 << 28) + +#define NV_PRAMDAC_PLL_SETUP_CONTROL 0x00680510 +#define NV_RAMDAC_VPLL2 0x00680520 +#define NV_PRAMDAC_SEL_CLK 0x00680524 +#define NV_RAMDAC_DITHER_NV11 0x00680528 +#define NV_PRAMDAC_DACCLK 0x0068052c +# define NV_PRAMDAC_DACCLK_SEL_DACCLK (1 << 0) + +#define NV_RAMDAC_NVPLL_B 0x00680570 +#define NV_RAMDAC_MPLL_B 0x00680574 +#define NV_RAMDAC_VPLL_B 0x00680578 +#define NV_RAMDAC_VPLL2_B 0x0068057c +# define NV31_RAMDAC_ENABLE_VCO2 (8 << 28) +#define NV_PRAMDAC_580 0x00680580 +# define NV_RAMDAC_580_VPLL1_ACTIVE (1 << 8) +# define NV_RAMDAC_580_VPLL2_ACTIVE (1 << 28) + +#define NV_PRAMDAC_GENERAL_CONTROL 0x00680600 +# define NV_PRAMDAC_GENERAL_CONTROL_PIXMIX_ON (3 << 4) +# define NV_PRAMDAC_GENERAL_CONTROL_VGA_STATE_SEL (1 << 8) +# define NV_PRAMDAC_GENERAL_CONTROL_ALT_MODE_SEL (1 << 12) +# define NV_PRAMDAC_GENERAL_CONTROL_TERMINATION_75OHM (2 << 16) +# define NV_PRAMDAC_GENERAL_CONTROL_BPC_8BITS (1 << 20) +# define NV_PRAMDAC_GENERAL_CONTROL_PIPE_LONG (2 << 28) +#define NV_PRAMDAC_TEST_CONTROL 0x00680608 +# define NV_PRAMDAC_TEST_CONTROL_TP_INS_EN_ASSERTED (1 << 12) +# define NV_PRAMDAC_TEST_CONTROL_PWRDWN_DAC_OFF (1 << 16) +# define NV_PRAMDAC_TEST_CONTROL_SENSEB_ALLHI (1 << 28) +#define NV_PRAMDAC_TESTPOINT_DATA 0x00680610 +# define NV_PRAMDAC_TESTPOINT_DATA_NOTBLANK (8 << 28) +#define NV_PRAMDAC_630 0x00680630 +#define NV_PRAMDAC_634 0x00680634 + +#define NV_PRAMDAC_TV_SETUP 0x00680700 +#define NV_PRAMDAC_TV_VTOTAL 0x00680720 +#define NV_PRAMDAC_TV_VSKEW 0x00680724 +#define NV_PRAMDAC_TV_VSYNC_DELAY 0x00680728 +#define NV_PRAMDAC_TV_HTOTAL 0x0068072c +#define NV_PRAMDAC_TV_HSKEW 0x00680730 +#define NV_PRAMDAC_TV_HSYNC_DELAY 0x00680734 +#define NV_PRAMDAC_TV_HSYNC_DELAY2 0x00680738 + +#define NV_PRAMDAC_TV_SETUP 0x00680700 + +#define NV_PRAMDAC_FP_VDISPLAY_END 0x00680800 +#define NV_PRAMDAC_FP_VTOTAL 0x00680804 +#define NV_PRAMDAC_FP_VCRTC 0x00680808 +#define NV_PRAMDAC_FP_VSYNC_START 0x0068080c +#define NV_PRAMDAC_FP_VSYNC_END 0x00680810 +#define NV_PRAMDAC_FP_VVALID_START 0x00680814 +#define NV_PRAMDAC_FP_VVALID_END 0x00680818 +#define NV_PRAMDAC_FP_HDISPLAY_END 0x00680820 +#define NV_PRAMDAC_FP_HTOTAL 0x00680824 +#define NV_PRAMDAC_FP_HCRTC 0x00680828 +#define NV_PRAMDAC_FP_HSYNC_START 0x0068082c +#define NV_PRAMDAC_FP_HSYNC_END 0x00680830 +#define NV_PRAMDAC_FP_HVALID_START 0x00680834 +#define NV_PRAMDAC_FP_HVALID_END 0x00680838 + +#define NV_RAMDAC_FP_DITHER 0x0068083c +#define NV_PRAMDAC_FP_TG_CONTROL 0x00680848 +# define NV_PRAMDAC_FP_TG_CONTROL_VSYNC_POS (1 << 0) +# define NV_PRAMDAC_FP_TG_CONTROL_VSYNC_DISABLE (2 << 0) +# define NV_PRAMDAC_FP_TG_CONTROL_HSYNC_POS (1 << 4) +# define NV_PRAMDAC_FP_TG_CONTROL_HSYNC_DISABLE (2 << 4) +# define NV_PRAMDAC_FP_TG_CONTROL_MODE_SCALE (0 << 8) +# define NV_PRAMDAC_FP_TG_CONTROL_MODE_CENTER (1 << 8) +# define NV_PRAMDAC_FP_TG_CONTROL_MODE_NATIVE (2 << 8) +# define NV_PRAMDAC_FP_TG_CONTROL_READ_PROG (1 << 20) +# define NV_PRAMDAC_FP_TG_CONTROL_WIDTH_12 (1 << 24) +# define NV_PRAMDAC_FP_TG_CONTROL_DISPEN_POS (1 << 28) +# define NV_PRAMDAC_FP_TG_CONTROL_DISPEN_DISABLE (2 << 28) +#define NV_PRAMDAC_FP_MARGIN_COLOR 0x0068084c +#define NV_PRAMDAC_850 0x00680850 +#define NV_PRAMDAC_85C 0x0068085c +#define NV_PRAMDAC_FP_DEBUG_0 0x00680880 +# define NV_PRAMDAC_FP_DEBUG_0_XSCALE_ENABLE (1 << 0) +# define NV_PRAMDAC_FP_DEBUG_0_YSCALE_ENABLE (1 << 4) +/* This doesn't seem to be essential for tmds, but still often set */ +# define NV_RAMDAC_FP_DEBUG_0_TMDS_ENABLED (8 << 4) +# define NV_PRAMDAC_FP_DEBUG_0_XINTERP_BILINEAR (1 << 8) +# define NV_PRAMDAC_FP_DEBUG_0_YINTERP_BILINEAR (1 << 12) +# define NV_PRAMDAC_FP_DEBUG_0_XWEIGHT_ROUND (1 << 20) +# define NV_PRAMDAC_FP_DEBUG_0_YWEIGHT_ROUND (1 << 24) +# define NV_PRAMDAC_FP_DEBUG_0_PWRDOWN_FPCLK (1 << 28) +#define NV_PRAMDAC_FP_DEBUG_1 0x00680884 +# define NV_PRAMDAC_FP_DEBUG_1_XSCALE_VALUE 11:0 +# define NV_PRAMDAC_FP_DEBUG_1_XSCALE_TESTMODE_ENABLE (1 << 12) +# define NV_PRAMDAC_FP_DEBUG_1_YSCALE_VALUE 27:16 +# define NV_PRAMDAC_FP_DEBUG_1_YSCALE_TESTMODE_ENABLE (1 << 28) +#define NV_PRAMDAC_FP_DEBUG_2 0x00680888 +#define NV_PRAMDAC_FP_DEBUG_3 0x0068088C + +/* see NV_PRAMDAC_INDIR_TMDS in rules.xml */ +#define NV_PRAMDAC_FP_TMDS_CONTROL 0x006808b0 +# define NV_PRAMDAC_FP_TMDS_CONTROL_WRITE_DISABLE (1 << 16) +#define NV_PRAMDAC_FP_TMDS_DATA 0x006808b4 + +#define NV_PRAMDAC_8C0 0x006808c0 + +/* Some kind of switch */ +#define NV_PRAMDAC_900 0x00680900 +#define NV_PRAMDAC_A20 0x00680A20 +#define NV_PRAMDAC_A24 0x00680A24 +#define NV_PRAMDAC_A34 0x00680A34 + +#define NV_PRAMDAC_CTV 0x00680c00 + +/* names fabricated from NV_USER_DAC info */ +#define NV_PRMDIO_PIXEL_MASK 0x006813c6 +# define NV_PRMDIO_PIXEL_MASK_MASK 0xff +#define NV_PRMDIO_READ_MODE_ADDRESS 0x006813c7 +#define NV_PRMDIO_WRITE_MODE_ADDRESS 0x006813c8 +#define NV_PRMDIO_PALETTE_DATA 0x006813c9 + +#define NV_PGRAPH_DEBUG_0 0x00400080 +#define NV_PGRAPH_DEBUG_1 0x00400084 +#define NV_PGRAPH_DEBUG_2_NV04 0x00400088 +#define NV_PGRAPH_DEBUG_2 0x00400620 +#define NV_PGRAPH_DEBUG_3 0x0040008c +#define NV_PGRAPH_DEBUG_4 0x00400090 +#define NV_PGRAPH_INTR 0x00400100 +#define NV_PGRAPH_INTR_EN 0x00400140 +#define NV_PGRAPH_CTX_CONTROL 0x00400144 +#define NV_PGRAPH_CTX_CONTROL_NV04 0x00400170 +#define NV_PGRAPH_ABS_UCLIP_XMIN 0x0040053C +#define NV_PGRAPH_ABS_UCLIP_YMIN 0x00400540 +#define NV_PGRAPH_ABS_UCLIP_XMAX 0x00400544 +#define NV_PGRAPH_ABS_UCLIP_YMAX 0x00400548 +#define NV_PGRAPH_BETA_AND 0x00400608 +#define NV_PGRAPH_LIMIT_VIOL_PIX 0x00400610 +#define NV_PGRAPH_BOFFSET0 0x00400640 +#define NV_PGRAPH_BOFFSET1 0x00400644 +#define NV_PGRAPH_BOFFSET2 0x00400648 +#define NV_PGRAPH_BLIMIT0 0x00400684 +#define NV_PGRAPH_BLIMIT1 0x00400688 +#define NV_PGRAPH_BLIMIT2 0x0040068c +#define NV_PGRAPH_STATUS 0x00400700 +#define NV_PGRAPH_SURFACE 0x00400710 +#define NV_PGRAPH_STATE 0x00400714 +#define NV_PGRAPH_FIFO 0x00400720 +#define NV_PGRAPH_PATTERN_SHAPE 0x00400810 +#define NV_PGRAPH_TILE 0x00400b00 + +#define NV_PVIDEO_INTR_EN 0x00008140 +#define NV_PVIDEO_BUFFER 0x00008700 +#define NV_PVIDEO_STOP 0x00008704 +#define NV_PVIDEO_UVPLANE_BASE(buff) (0x00008800+(buff)*4) +#define NV_PVIDEO_UVPLANE_LIMIT(buff) (0x00008808+(buff)*4) +#define NV_PVIDEO_UVPLANE_OFFSET_BUFF(buff) (0x00008820+(buff)*4) +#define NV_PVIDEO_BASE(buff) (0x00008900+(buff)*4) +#define NV_PVIDEO_LIMIT(buff) (0x00008908+(buff)*4) +#define NV_PVIDEO_LUMINANCE(buff) (0x00008910+(buff)*4) +#define NV_PVIDEO_CHROMINANCE(buff) (0x00008918+(buff)*4) +#define NV_PVIDEO_OFFSET_BUFF(buff) (0x00008920+(buff)*4) +#define NV_PVIDEO_SIZE_IN(buff) (0x00008928+(buff)*4) +#define NV_PVIDEO_POINT_IN(buff) (0x00008930+(buff)*4) +#define NV_PVIDEO_DS_DX(buff) (0x00008938+(buff)*4) +#define NV_PVIDEO_DT_DY(buff) (0x00008940+(buff)*4) +#define NV_PVIDEO_POINT_OUT(buff) (0x00008948+(buff)*4) +#define NV_PVIDEO_SIZE_OUT(buff) (0x00008950+(buff)*4) +#define NV_PVIDEO_FORMAT(buff) (0x00008958+(buff)*4) +# define NV_PVIDEO_FORMAT_PLANAR (1 << 0) +# define NV_PVIDEO_FORMAT_COLOR_LE_CR8YB8CB8YA8 (1 << 16) +# define NV_PVIDEO_FORMAT_DISPLAY_COLOR_KEY (1 << 20) +# define NV_PVIDEO_FORMAT_MATRIX_ITURBT709 (1 << 24) +#define NV_PVIDEO_COLOR_KEY 0x00008B00 + +/* NV04 overlay defines from VIDIX & Haiku */ +#define NV_PVIDEO_INTR_EN_0 0x00680140 +#define NV_PVIDEO_STEP_SIZE 0x00680200 +#define NV_PVIDEO_CONTROL_Y 0x00680204 +#define NV_PVIDEO_CONTROL_X 0x00680208 +#define NV_PVIDEO_BUFF0_START_ADDRESS 0x0068020c +#define NV_PVIDEO_BUFF0_PITCH_LENGTH 0x00680214 +#define NV_PVIDEO_BUFF0_OFFSET 0x0068021c +#define NV_PVIDEO_BUFF1_START_ADDRESS 0x00680210 +#define NV_PVIDEO_BUFF1_PITCH_LENGTH 0x00680218 +#define NV_PVIDEO_BUFF1_OFFSET 0x00680220 +#define NV_PVIDEO_OE_STATE 0x00680224 +#define NV_PVIDEO_SU_STATE 0x00680228 +#define NV_PVIDEO_RM_STATE 0x0068022c +#define NV_PVIDEO_WINDOW_START 0x00680230 +#define NV_PVIDEO_WINDOW_SIZE 0x00680234 +#define NV_PVIDEO_FIFO_THRES_SIZE 0x00680238 +#define NV_PVIDEO_FIFO_BURST_LENGTH 0x0068023c +#define NV_PVIDEO_KEY 0x00680240 +#define NV_PVIDEO_OVERLAY 0x00680244 +#define NV_PVIDEO_RED_CSC_OFFSET 0x00680280 +#define NV_PVIDEO_GREEN_CSC_OFFSET 0x00680284 +#define NV_PVIDEO_BLUE_CSC_OFFSET 0x00680288 +#define NV_PVIDEO_CSC_ADJUST 0x0068028c + +#endif diff --git a/driver/pscnv/pscnv_chan.c b/driver/pscnv/pscnv_chan.c new file mode 100644 index 00000000..78ac8ed3 --- /dev/null +++ b/driver/pscnv/pscnv_chan.c @@ -0,0 +1,235 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "pscnv_mem.h" +#include "pscnv_vm.h" +#include "pscnv_ramht.h" +#include "pscnv_chan.h" +#include "pscnv_fifo.h" +#include "pscnv_ioctl.h" + +static int pscnv_chan_bind (struct pscnv_chan *ch, int fake) { + struct drm_nouveau_private *dev_priv = ch->dev->dev_private; + unsigned long flags; + int i; + BUG_ON(ch->cid); + spin_lock_irqsave(&dev_priv->chan->ch_lock, flags); + if (fake) { + ch->cid = -fake; + BUG_ON(dev_priv->chan->fake_chans[fake]); + dev_priv->chan->fake_chans[fake] = ch; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + return 0; + } else { + for (i = dev_priv->chan->ch_min; i <= dev_priv->chan->ch_max; i++) + if (!dev_priv->chan->chans[i]) { + ch->cid = i; + dev_priv->chan->chans[i] = ch; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + return 0; + } + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + NV_ERROR(ch->dev, "CHAN: Out of channels\n"); + return -ENOSPC; + } +} + +static void pscnv_chan_unbind (struct pscnv_chan *ch) { + struct drm_nouveau_private *dev_priv = ch->dev->dev_private; + unsigned long flags; + spin_lock_irqsave(&dev_priv->chan->ch_lock, flags); + if (ch->cid < 0) { + BUG_ON(dev_priv->chan->fake_chans[-ch->cid] != ch); + dev_priv->chan->fake_chans[-ch->cid] = 0; + } else { + BUG_ON(dev_priv->chan->chans[ch->cid] != ch); + dev_priv->chan->chans[ch->cid] = 0; + } + ch->cid = 0; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); +} + +struct pscnv_chan * +pscnv_chan_new (struct drm_device *dev, struct pscnv_vspace *vs, int fake) { + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + struct pscnv_chan *res = kzalloc(sizeof *res, GFP_KERNEL); + if (!res) { + NV_ERROR(vs->dev, "CHAN: Couldn't alloc channel\n"); + return 0; + } + res->dev = dev; + res->vspace = vs; + res->handle = 0xffffffff; + if (vs) + pscnv_vspace_ref(vs); + spin_lock_init(&res->instlock); + spin_lock_init(&res->ramht.lock); + kref_init(&res->ref); + if (pscnv_chan_bind(res, fake)) { + if (vs) + pscnv_vspace_unref(vs); + kfree(res); + return 0; + } + //NV_INFO(vs->dev, "CHAN: Allocating channel %d\n", res->cid); + if (dev_priv->chan->do_chan_new(res)) { + if (vs) + pscnv_vspace_unref(vs); + pscnv_chan_unbind(res); + kfree(res); + return 0; + } + + return res; +} + +void pscnv_chan_ref_free(struct kref *ref) { + struct pscnv_chan *ch = container_of(ref, struct pscnv_chan, ref); + struct drm_device *dev = ch->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + + //NV_INFO(dev, "CHAN: Freeing channel %d\n", ch->cid); + + if (ch->cid >= 0) { + int i; + dev_priv->fifo->chan_kill(ch); + for (i = 0; i < PSCNV_ENGINES_NUM; i++) + if (ch->engdata[i]) { + struct pscnv_engine *eng = dev_priv->engines[i]; + eng->chan_kill(eng, ch); + eng->chan_free(eng, ch); + } + } + dev_priv->chan->do_chan_free(ch); + pscnv_chan_unbind(ch); + if (ch->vspace) + pscnv_vspace_unref(ch->vspace); + kfree(ch); +} + +static void pscnv_chan_vm_open(struct vm_area_struct *vma) { + struct pscnv_chan *ch = vma->vm_private_data; + pscnv_chan_ref(ch); +} + +static void pscnv_chan_vm_close(struct vm_area_struct *vma) { + struct pscnv_chan *ch = vma->vm_private_data; + pscnv_chan_unref(ch); +} + +static struct vm_operations_struct pscnv_chan_vm_ops = { + .open = pscnv_chan_vm_open, + .close = pscnv_chan_vm_close, +}; + +/* XXX */ +extern uint64_t nvc0_fifo_ctrl_offs(struct drm_device *dev, int cid); + +int pscnv_chan_mmap(struct file *filp, struct vm_area_struct *vma) +{ + struct drm_file *priv = filp->private_data; + struct drm_device *dev = priv->minor->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + int cid; + struct pscnv_chan *ch; + + switch (dev_priv->card_type) { + case NV_50: + if ((vma->vm_pgoff * PAGE_SIZE & ~0x7f0000ull) == 0xc0000000) { + if (vma->vm_end - vma->vm_start > 0x2000) + return -EINVAL; + cid = (vma->vm_pgoff * PAGE_SIZE >> 16) & 0x7f; + ch = pscnv_get_chan(dev, filp->private_data, cid); + if (!ch) + return -ENOENT; + + vma->vm_flags |= VM_RESERVED | VM_IO | VM_PFNMAP | VM_DONTEXPAND; + vma->vm_ops = &pscnv_chan_vm_ops; + vma->vm_private_data = ch; + + vma->vm_file = filp; + + return remap_pfn_range(vma, vma->vm_start, + (dev_priv->mmio_phys + 0xc00000 + cid * 0x2000) >> PAGE_SHIFT, + vma->vm_end - vma->vm_start, PAGE_SHARED); + } + break; + case NV_C0: + if ((vma->vm_pgoff * PAGE_SIZE & ~0x7f0000ull) == 0xc0000000) { + if (vma->vm_end - vma->vm_start > 0x1000) + return -EINVAL; + cid = (vma->vm_pgoff * PAGE_SIZE >> 16) & 0x7f; + ch = pscnv_get_chan(dev, filp->private_data, cid); + if (!ch) + return -ENOENT; + + vma->vm_flags |= VM_RESERVED | VM_IO | VM_PFNMAP | VM_DONTEXPAND; + vma->vm_ops = &pscnv_chan_vm_ops; + vma->vm_private_data = ch; + vma->vm_page_prot = pgprot_writecombine(vm_get_page_prot(vma->vm_flags)); + + vma->vm_file = filp; + + return remap_pfn_range(vma, vma->vm_start, + (dev_priv->fb_phys + nvc0_fifo_ctrl_offs(dev, ch->cid)) >> PAGE_SHIFT, + vma->vm_end - vma->vm_start, PAGE_SHARED); + } + default: + return -ENOSYS; + } + return -EINVAL; +} + +int pscnv_chan_handle_lookup(struct drm_device *dev, uint32_t handle) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + unsigned long flags; + struct pscnv_chan *res; + int i; + spin_lock_irqsave(&dev_priv->chan->ch_lock, flags); + for (i = 0; i < 128; i++) { + res = dev_priv->chan->chans[i]; + if (!res) + continue; + if (res->bo->start >> 12 != handle) + continue; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + return i; + } + for (i = 0; i < 4; i++) { + res = dev_priv->chan->fake_chans[i]; + if (!res) + continue; + if (res->handle != handle) + continue; + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + return -i; + } + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + return 128; +} diff --git a/driver/pscnv/pscnv_chan.h b/driver/pscnv/pscnv_chan.h new file mode 100644 index 00000000..13c9d253 --- /dev/null +++ b/driver/pscnv/pscnv_chan.h @@ -0,0 +1,81 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#ifndef __PSCNV_CHAN_H__ +#define __PSCNV_CHAN_H__ + +#include "pscnv_vm.h" +#include "pscnv_ramht.h" +#include "pscnv_engine.h" +#include + +struct pscnv_chan { + struct drm_device *dev; + int cid; + /* protected by ch_lock below, used for lookup */ + uint32_t handle; + struct pscnv_vspace *vspace; + struct list_head vspace_list; + struct pscnv_bo *bo; + spinlock_t instlock; + int instpos; + struct pscnv_ramht ramht; + uint32_t ramfc; + struct pscnv_bo *cache; + struct drm_file *filp; + struct kref ref; + void *engdata[PSCNV_ENGINES_NUM]; +}; + +struct pscnv_chan_engine { + void (*takedown) (struct drm_device *dev); + int (*do_chan_new) (struct pscnv_chan *ch); + void (*do_chan_free) (struct pscnv_chan *ch); + struct pscnv_chan *fake_chans[4]; + struct pscnv_chan *chans[128]; + spinlock_t ch_lock; + int ch_min, ch_max; +}; + +extern struct pscnv_chan *pscnv_chan_new(struct drm_device *dev, struct pscnv_vspace *, int fake); + +extern void pscnv_chan_ref_free(struct kref *ref); + +static inline void pscnv_chan_ref(struct pscnv_chan *ch) { + kref_get(&ch->ref); +} + +static inline void pscnv_chan_unref(struct pscnv_chan *ch) { + kref_put(&ch->ref, pscnv_chan_ref_free); +} + +extern int pscnv_chan_mmap(struct file *filp, struct vm_area_struct *vma); +extern int pscnv_chan_handle_lookup(struct drm_device *dev, uint32_t handle); + +int nv50_chan_init(struct drm_device *dev); +int nvc0_chan_init(struct drm_device *dev); + +#endif diff --git a/driver/pscnv/pscnv_drm.h b/driver/pscnv/pscnv_drm.h new file mode 100644 index 00000000..b1328c75 --- /dev/null +++ b/driver/pscnv/pscnv_drm.h @@ -0,0 +1,173 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#ifndef __PSCNV_DRM_H__ +#define __PSCNV_DRM_H__ + +#define PSCNV_DRM_HEADER_PATCHLEVEL 1 + +#define PSCNV_GETPARAM_PCI_VENDOR 3 +#define PSCNV_GETPARAM_PCI_DEVICE 4 +#define PSCNV_GETPARAM_BUS_TYPE 5 +#define PSCNV_GETPARAM_FB_SIZE 8 +#define PSCNV_GETPARAM_CHIPSET_ID 11 +#define PSCNV_GETPARAM_GRAPH_UNITS 13 +#define PSCNV_GETPARAM_PTIMER_TIME 14 +#define PSCNV_GETPARAM_MP_COUNT 100 +struct drm_pscnv_getparam { + uint64_t param; /* < */ + uint64_t value; /* > */ +}; + +enum pscnv_bus_type { + NV_AGP = 0, + NV_PCI = 1, + NV_PCIE = 2, +}; + +/* used for gem_new and gem_info */ +struct drm_pscnv_gem_info { /* n i */ + /* GEM handle used for identification */ + uint32_t handle; /* > < */ + /* cookie: free-form 32-bit number displayed in debug info. */ + uint32_t cookie; /* < > */ + /* misc flags, see below. */ + uint32_t flags; /* < > */ + uint32_t tile_flags; /* < > */ + uint64_t size; /* < > */ + /* offset inside drm fd's vm space usable for mmapping */ + uint64_t map_handle; /* > > */ + /* unused by kernel, can be used by userspace to store some info, + * like buffer format and tile_mode for DRI2 */ + uint32_t user[8]; /* < > */ +}; +#define PSCNV_GEM_CONTIG 0x00000001 /* needs to be contiguous in VRAM */ +#define PSCNV_GEM_MAPPABLE 0x00000002 /* intended to be mmapped by host */ +#define PSCNV_GEM_MEMTYPE_MASK 0x0000000c +#define PSCNV_GEM_VRAM_SMALL 0x00000000 /* VRAM with small pages */ +#define PSCNV_GEM_SYSRAM_SNOOP 0x00000004 +#define PSCNV_GEM_VRAM_LARGE 0x00000008 /* VRAM with large pages */ +#define PSCNV_GEM_SYSRAM_NOSNOOP 0x0000000c +#define PSCNV_GEM_GART PSCNV_GEM_SYSRAM_SNOOP /* compat */ + +/* for vspace_new and vspace_free */ +struct drm_pscnv_vspace_req { /* n f */ + uint32_t vid; /* > < */ +}; + +struct drm_pscnv_vspace_map { + uint32_t vid; /* < */ + uint32_t handle; /* < */ + uint64_t start; /* < */ + uint64_t end; /* < */ + uint32_t back; /* < */ + /* none defined yet */ + uint32_t flags; /* < */ + uint64_t offset; /* > */ +}; + +struct drm_pscnv_vspace_unmap { + uint32_t vid; /* < */ + uint32_t _pad; + uint64_t offset; /* < */ +}; + +struct drm_pscnv_chan_new { + uint32_t vid; /* < */ + uint32_t cid; /* > */ + /* The map handle that can be used to access channel control regs */ + uint64_t map_handle; /* > */ +}; + +struct drm_pscnv_chan_free { + uint32_t cid; /* < */ +}; + +struct drm_pscnv_obj_vdma_new { + uint32_t cid; /* < */ + uint32_t handle; /* < */ + uint32_t oclass; /* < */ + uint32_t flags; /* < */ + uint64_t start; /* < */ + uint64_t size; /* < */ +}; + +struct drm_pscnv_fifo_init { + uint32_t cid; /* < */ + uint32_t pb_handle; /* < */ + uint32_t flags; /* < */ + uint32_t slimask; /* < */ + uint64_t pb_start; /* < */ +}; + +struct drm_pscnv_fifo_init_ib { + uint32_t cid; /* < */ + uint32_t pb_handle; /* < */ + uint32_t flags; /* < */ + uint32_t slimask; /* < */ + uint64_t ib_start; /* < */ + uint32_t ib_order; /* < */ + uint32_t _pad; +}; + +struct drm_pscnv_obj_eng_new { + uint32_t cid; /* < */ + uint32_t handle; /* < */ + uint32_t oclass; /* < */ + uint32_t flags; /* < */ +}; + +#define DRM_PSCNV_GETPARAM 0x00 /* get some information from the card */ +#define DRM_PSCNV_GEM_NEW 0x20 /* create a new BO */ +#define DRM_PSCNV_GEM_INFO 0x21 /* get info about a BO */ +/* also uses generic GEM close, flink, open ioctls */ +#define DRM_PSCNV_VSPACE_NEW 0x22 /* Create a new virtual address space */ +#define DRM_PSCNV_VSPACE_FREE 0x23 /* Free a virtual address space */ +#define DRM_PSCNV_VSPACE_MAP 0x24 /* Maps a BO to a vspace */ +#define DRM_PSCNV_VSPACE_UNMAP 0x25 /* Unmaps a BO from a vspace */ +#define DRM_PSCNV_CHAN_NEW 0x26 /* Create a new channel */ +#define DRM_PSCNV_CHAN_FREE 0x27 /* Free a channel */ +#define DRM_PSCNV_OBJ_VDMA_NEW 0x28 /* Create a new vspace DMA object on a channel */ +#define DRM_PSCNV_FIFO_INIT 0x29 /* Initialises PFIFO processing on a channel */ +#define DRM_PSCNV_OBJ_ENG_NEW 0x2a /* Create a new engine object on a channel */ +#define DRM_PSCNV_FIFO_INIT_IB 0x2b /* Initialises IB PFIFO processing on a channel */ + +#define DRM_IOCTL_PSCNV_GETPARAM DRM_IOWR(DRM_COMMAND_BASE + DRM_PSCNV_GETPARAM, struct drm_pscnv_getparam) +#define DRM_IOCTL_PSCNV_GEM_NEW DRM_IOWR(DRM_COMMAND_BASE + DRM_PSCNV_GEM_NEW, struct drm_pscnv_gem_info) +#define DRM_IOCTL_PSCNV_GEM_INFO DRM_IOWR(DRM_COMMAND_BASE + DRM_PSCNV_GEM_INFO, struct drm_pscnv_gem_info) +/* also uses generic GEM close, flink, open ioctls */ +#define DRM_IOCTL_PSCNV_VSPACE_NEW DRM_IOR(DRM_COMMAND_BASE + DRM_PSCNV_VSPACE_NEW, struct drm_pscnv_vspace_req) +#define DRM_IOCTL_PSCNV_VSPACE_FREE DRM_IOW(DRM_COMMAND_BASE + DRM_PSCNV_VSPACE_FREE, struct drm_pscnv_vspace_req) +#define DRM_IOCTL_PSCNV_VSPACE_MAP DRM_IOWR(DRM_COMMAND_BASE + DRM_PSCNV_VSPACE_MAP, struct drm_pscnv_vspace_map) +#define DRM_IOCTL_PSCNV_VSPACE_UNMAP DRM_IOW(DRM_COMMAND_BASE + DRM_PSCNV_VSPACE_UNMAP, struct drm_pscnv_vspace_unmap) +#define DRM_IOCTL_PSCNV_CHAN_NEW DRM_IOWR(DRM_COMMAND_BASE + DRM_PSCNV_CHAN_NEW, struct drm_pscnv_chan_new) +#define DRM_IOCTL_PSCNV_CHAN_FREE DRM_IOW(DRM_COMMAND_BASE + DRM_PSCNV_CHAN_FREE, struct drm_pscnv_chan_free) +#define DRM_IOCTL_PSCNV_OBJ_VDMA_NEW DRM_IOW(DRM_COMMAND_BASE + DRM_PSCNV_OBJ_VDMA_NEW, struct drm_pscnv_obj_vdma_new) +#define DRM_IOCTL_PSCNV_FIFO_INIT DRM_IOW(DRM_COMMAND_BASE + DRM_PSCNV_FIFO_INIT, struct drm_pscnv_fifo_init) +#define DRM_IOCTL_PSCNV_OBJ_ENG_NEW DRM_IOW(DRM_COMMAND_BASE + DRM_PSCNV_OBJ_ENG_NEW, struct drm_pscnv_obj_eng_new) +#define DRM_IOCTL_PSCNV_FIFO_INIT_IB DRM_IOW(DRM_COMMAND_BASE + DRM_PSCNV_FIFO_INIT_IB, struct drm_pscnv_fifo_init_ib) + +#endif /* __PSCNV_DRM_H__ */ diff --git a/driver/pscnv/pscnv_engine.h b/driver/pscnv/pscnv_engine.h new file mode 100644 index 00000000..d2d96e75 --- /dev/null +++ b/driver/pscnv/pscnv_engine.h @@ -0,0 +1,33 @@ +#ifndef __PSCNV_ENGINE_H__ +#define __PSCNV_ENGINE_H__ + +struct pscnv_chan; +struct pscnv_vspace; + +struct pscnv_engine { + struct drm_device *dev; + uint32_t *oclasses; + void (*takedown) (struct pscnv_engine *eng); + int (*tlb_flush) (struct pscnv_engine *eng, struct pscnv_vspace *vs); + int (*chan_alloc) (struct pscnv_engine *eng, struct pscnv_chan *ch); + void (*chan_free) (struct pscnv_engine *eng, struct pscnv_chan *ch); + int (*chan_obj_new) (struct pscnv_engine *eng, struct pscnv_chan *ch, uint32_t handle, uint32_t oclass, uint32_t flags); + void (*chan_kill) (struct pscnv_engine *eng, struct pscnv_chan *ch); +}; + +int nv50_graph_init(struct drm_device *dev); +int nvc0_graph_init(struct drm_device *dev); +int nv84_crypt_init(struct drm_device *dev); +int nv98_crypt_init(struct drm_device *dev); +int nvc0_copy_init(struct drm_device *dev, int engine); + +#define PSCNV_ENGINE_GRAPH 1 +#define PSCNV_ENGINE_COPY 3 +#define PSCNV_ENGINE_COPY0 3 /* PSCNV_ENGINE_COPY + 0 */ +#define PSCNV_ENGINE_COPY1 4 /* PSCNV_ENGINE_COPY + 1 */ +#define PSCNV_ENGINE_CRYPT 5 + +#define PSCNV_ENGINES_NUM 16 + + +#endif diff --git a/driver/pscnv/pscnv_fifo.h b/driver/pscnv/pscnv_fifo.h new file mode 100644 index 00000000..743cca8d --- /dev/null +++ b/driver/pscnv/pscnv_fifo.h @@ -0,0 +1,40 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#ifndef __PSCNV_FIFO_H__ +#define __PSCNV_FIFO_H__ + +struct pscnv_fifo_engine { + void (*takedown) (struct drm_device *dev); + int (*chan_init_dma) (struct pscnv_chan *ch, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t pb_start); + int (*chan_init_ib) (struct pscnv_chan *ch, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t ib_start, uint32_t ib_order); + void (*chan_kill) (struct pscnv_chan *ch); +}; + +int nv50_fifo_init(struct drm_device *dev); +int nvc0_fifo_init(struct drm_device *dev); + +#endif diff --git a/driver/pscnv/pscnv_gdev.c b/driver/pscnv/pscnv_gdev.c new file mode 100644 index 00000000..05058ee3 --- /dev/null +++ b/driver/pscnv/pscnv_gdev.c @@ -0,0 +1,377 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "gdev_conf.h" +#include "gdev_drv.h" +#include "nouveau_drv.h" +#include "pscnv_chan.h" +#include "pscnv_fifo.h" +#include "pscnv_gem.h" +#include "pscnv_ioctl.h" +#include "pscnv_mem.h" +#include "pscnv_vm.h" + +extern uint32_t *nvc0_fifo_ctrl_ptr(struct drm_device *, struct pscnv_chan *); + +/* allocate a new memory object. */ +static inline gdev_mem_t *__gdev_mem_alloc +(gdev_vas_t *vas, uint64_t size, uint32_t flags) +{ + gdev_mem_t *mem; + gdev_device_t *gdev = vas->gdev; + struct drm_device *drm = gdev->drm; + struct pscnv_vspace *vspace = vas->pvas; + struct pscnv_bo *bo; + struct pscnv_mm_node *mm; + + if (!(mem = kzalloc(sizeof(*mem), GFP_KERNEL))) + goto fail_mem; + + if (!(bo = pscnv_mem_alloc(drm, size, flags, 0, 0))) + goto fail_bo; + + if (pscnv_vspace_map(vspace, bo, GDEV_VAS_USER_START, + GDEV_VAS_USER_END, 0, &mm)) + goto fail_map; + + mem->vas = vas; + mem->bo = bo; + mem->addr = mm->start; + if (flags & PSCNV_GEM_SYSRAM_SNOOP) { + if (size > PAGE_SIZE) + mem->map = vmap(bo->pages, bo->size >> PAGE_SHIFT, 0, PAGE_KERNEL); + else + mem->map = kmap(bo->pages[0]); + } + else + mem->map = NULL; + + __gdev_list_init(&mem->list_entry, (void *)mem); + + return mem; + +fail_map: + GDEV_PRINT("Failed to map VAS.\n"); + pscnv_mem_free(bo); +fail_bo: + GDEV_PRINT("Failed to allocate buffer object.\n"); + kfree(mem); +fail_mem: + return NULL; +} + +/* free the specified memory object. */ +static inline void __gdev_mem_free(gdev_mem_t *mem) +{ + gdev_vas_t *vas = mem->vas; + struct pscnv_vspace *vspace = vas->pvas; + struct pscnv_bo *bo = mem->bo; + + if (mem->map) { + if (bo->size > PAGE_SIZE) + vunmap(mem->map); + else + kunmap(mem->map); + } + pscnv_vspace_unmap(vspace, mem->addr); + pscnv_mem_free(mem->bo); + kfree(mem); +} + +/* initialize the compute engine. */ +int gdev_compute_init(gdev_device_t *gdev) +{ + struct drm_device *drm = gdev->drm; + struct drm_nouveau_private *priv = drm->dev_private; + uint32_t chipset = priv->chipset; + + switch (chipset & 0xf0) { + case 0xC0: + nvc0_compute_setup(gdev); + break; + case 0x50: + case 0x80: + case 0x90: + case 0xA0: + /* TODO: create the compute and m2mf subchannels! */ + GDEV_PRINT("NV%x not supported.\n", chipset); + return -EINVAL; + default: + GDEV_PRINT("NV%x not supported.\n", chipset); + return -EINVAL; + } + + return 0; +} + +/* query a piece of the device-specific information. */ +int gdev_info_query(gdev_device_t *gdev, uint32_t type, uint32_t *result) +{ + struct drm_device *drm = gdev->drm; + struct drm_nouveau_private *priv = drm->dev_private; + struct drm_pscnv_getparam getparam; + uint32_t chipset = priv->chipset; + + switch (type) { + case GDEV_QUERY_NVIDIA_MP_COUNT: + if ((chipset & 0xf0) != 0xc0) + return -EINVAL; + getparam.param = PSCNV_GETPARAM_MP_COUNT; + pscnv_ioctl_getparam(drm, &getparam, NULL); + *result = getparam.value; + break; + default: + return -EINVAL; + } + + return 0; +} + +/* open a new Gdev object associated with the specified device. */ +gdev_device_t *gdev_dev_open(int devnum) +{ + gdev_device_t *gdev = &gdrv.gdev[devnum]; + gdev->use++; + return gdev; +} + +/* close the specified Gdev object. */ +void gdev_dev_close(gdev_device_t *gdev) +{ + gdev->use--; +} + +/* allocate a new virual address space object. */ +gdev_vas_t *gdev_vas_new(gdev_device_t *gdev, uint64_t size) +{ + gdev_vas_t *vas; + struct drm_device *drm = gdev->drm; + struct pscnv_vspace *vspace; + + if (!(vas = kzalloc(sizeof(*vas), GFP_KERNEL))) + goto fail_vas; + + if (!(vspace = pscnv_vspace_new(drm, size, 0, 0))) + goto fail_vspace; + + /* we don't need vspace->filp in Gdev. */ + vspace->filp = NULL; + + vas->gdev = gdev; + vas->pvas = vspace; /* driver private object. */ + + __gdev_list_init(&vas->memlist, NULL); + + return vas; + +fail_vspace: + kfree(vas); +fail_vas: + return NULL; +} + +/* free the specified virtual address space object. */ +void gdev_vas_free(gdev_vas_t *vas) +{ + struct pscnv_vspace *vspace = vas->pvas; + + vspace->filp = NULL; + pscnv_vspace_unref(vspace); + + kfree(vas); +} + +/* create a new GPU context object. */ +gdev_ctx_t *gdev_ctx_new(gdev_device_t *gdev, gdev_vas_t *vas) +{ + gdev_ctx_t *ctx; + struct gdev_compute *compute = gdev->compute; + struct drm_device *drm = gdev->drm; + struct drm_nouveau_private *priv = drm->dev_private; + uint32_t chipset = priv->chipset; + struct pscnv_vspace *vspace = vas->pvas; + struct pscnv_chan *chan; + struct pscnv_bo *ib_bo, *pb_bo, *fence_bo; + struct pscnv_mm_node *ib_mm, *pb_mm, *fence_mm; + int i, ret; + + ctx = kzalloc(sizeof(*ctx), GFP_KERNEL); + if (!ctx) + goto fail_ctx; + + chan = pscnv_chan_new(drm, vspace, 0); + if (!chan) + goto fail_chan; + + /* we don't need chan->filp in Gdev. */ + chan->filp = NULL; + + if ((chipset & 0xf0) != 0xc0) { + /* TODO: set up vdma here! */ + } + + /* FIFO indirect buffer setup. */ + ctx->fifo.ib_order = 9; /* it's hardcoded. */ + ib_bo = pscnv_mem_alloc(drm, 8 << ctx->fifo.ib_order, + PSCNV_GEM_SYSRAM_SNOOP, 0, 0); + if (!ib_bo) { + goto fail_ib; + } + ret = pscnv_vspace_map(vspace, ib_bo, GDEV_VAS_USER_START, + GDEV_VAS_USER_END, 0, &ib_mm); + if (ret) + goto fail_ibmap; + ctx->fifo.ib_map = vmap(ib_bo->pages, ib_bo->size >> PAGE_SHIFT, 0, + PAGE_KERNEL); + ctx->fifo.ib_bo = ib_bo; + ctx->fifo.ib_base = ib_mm->start; + ctx->fifo.ib_mask = (1 << ctx->fifo.ib_order) - 1; + ctx->fifo.ib_put = ctx->fifo.ib_get = 0; + + /* FIFO push buffer setup. */ + ctx->fifo.pb_order = 20; /* it's hardcoded. */ + pb_bo = pscnv_mem_alloc(drm, 1 << ctx->fifo.pb_order, + PSCNV_GEM_SYSRAM_SNOOP, 0, 0); + if (!pb_bo) + goto fail_pb; + ret = pscnv_vspace_map(vspace, pb_bo, GDEV_VAS_USER_START, + GDEV_VAS_USER_END, 0, &pb_mm); + if (ret) + goto fail_pbmap; + ctx->fifo.pb_map = vmap(pb_bo->pages, pb_bo->size >> PAGE_SHIFT, 0, + PAGE_KERNEL); + ctx->fifo.pb_bo = pb_bo; + ctx->fifo.pb_base = pb_mm->start; + ctx->fifo.pb_mask = (1 << ctx->fifo.pb_order) - 1; + ctx->fifo.pb_size = (1 << ctx->fifo.pb_order); + ctx->fifo.pb_pos = ctx->fifo.pb_put = ctx->fifo.pb_get = 0; + + /* FIFO init. */ + ret = priv->fifo->chan_init_ib(chan, 0, 0, 1, + ctx->fifo.ib_base, ctx->fifo.ib_order); + if (ret) + goto fail_fifo_init; + + /* FIFO command queue registers. */ + switch (chipset & 0xf0) { + case 0xc0: + ctx->fifo.regs = nvc0_fifo_ctrl_ptr(drm, chan); + break; + default: + goto fail_fifo_reg; + } + + /* fences init. */ + fence_bo = pscnv_mem_alloc(drm, PAGE_SIZE, PSCNV_GEM_SYSRAM_SNOOP, 0, 0); + if (!fence_bo) + goto fail_fence_alloc; + ret = pscnv_vspace_map(vspace, fence_bo, GDEV_VAS_USER_START, + GDEV_VAS_USER_END, 0, &fence_mm); + if (ret) + goto fail_fence_map; + ctx->fence.bo = fence_bo; + ctx->fence.map = kmap(fence_bo->pages[0]); /* assume < PAGE_SIZE */ + ctx->fence.addr = fence_mm->start; + for (i = 0; i < GDEV_FENCE_COUNT; i++) { + ctx->fence.sequence[i] = 0; + } + + ctx->vas = vas; + ctx->pctx = chan; + + /* initialize the channel. */ + compute->init(ctx); + + return ctx; + +fail_fence_map: + pscnv_mem_free(fence_bo); +fail_fence_alloc: +fail_fifo_reg: +fail_fifo_init: + vunmap(ctx->fifo.pb_map); + pscnv_vspace_unmap(vspace, pb_mm->start); +fail_pbmap: + pscnv_mem_free(pb_bo); +fail_pb: + vunmap(ctx->fifo.ib_map); + pscnv_vspace_unmap(vspace, ib_mm->start); +fail_ibmap: + pscnv_mem_free(ib_bo); +fail_ib: + chan->filp = NULL; + pscnv_chan_unref(chan); +fail_chan: + kfree(ctx); +fail_ctx: + return NULL; +} + +/* destroy the specified GPU context object. */ +void gdev_ctx_free(gdev_ctx_t *ctx) +{ + gdev_vas_t *vas = ctx->vas; + struct pscnv_vspace *vspace = vas->pvas; + struct pscnv_chan *chan = ctx->pctx; + struct pscnv_bo *fence_bo = ctx->fence.bo; + + kunmap(fence_bo->pages[0]); + pscnv_vspace_unmap(vspace, ctx->fence.addr); + pscnv_mem_free((struct pscnv_bo *)ctx->fence.bo); + vunmap(ctx->fifo.pb_map); + pscnv_vspace_unmap(vspace, ctx->fifo.pb_base); + pscnv_mem_free((struct pscnv_bo *)ctx->fifo.pb_bo); + vunmap(ctx->fifo.ib_map); + pscnv_vspace_unmap(vspace, ctx->fifo.ib_base); + pscnv_mem_free((struct pscnv_bo *)ctx->fifo.ib_bo); + + chan->filp = NULL; + pscnv_chan_unref(chan); + + kfree(ctx); +} + +/* allocate a new device memory object. */ +gdev_mem_t *gdev_malloc_device(gdev_vas_t *vas, uint64_t size) +{ + return __gdev_mem_alloc(vas, size, PSCNV_GEM_VRAM_SMALL); +} + +/* free the specified device memory object. */ +void gdev_free_device(gdev_mem_t *mem) +{ + return __gdev_mem_free(mem); +} + +/* allocate a new DMA (host) memory object. */ +gdev_mem_t *gdev_malloc_dma(gdev_vas_t *vas, uint64_t size) +{ + return __gdev_mem_alloc(vas, size, PSCNV_GEM_SYSRAM_SNOOP); +} + +/* free the specified DMA (host) memory object. */ +void gdev_free_dma(gdev_mem_t *mem) +{ + return __gdev_mem_free(mem); +} diff --git a/driver/pscnv/pscnv_gem.c b/driver/pscnv/pscnv_gem.c new file mode 100644 index 00000000..58e941aa --- /dev/null +++ b/driver/pscnv/pscnv_gem.c @@ -0,0 +1,74 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "pscnv_gem.h" +#include "pscnv_mem.h" +#include "pscnv_drm.h" + +void pscnv_gem_free_object (struct drm_gem_object *obj) { + struct pscnv_bo *vo = obj->driver_private; +#ifndef PSCNV_KAPI_DRM_GEM_OBJECT_HANDLE_COUNT + atomic_dec(&obj->handle_count); +#endif + pscnv_mem_free(vo); + drm_gem_object_release(obj); + kfree(obj); +} + +struct drm_gem_object *pscnv_gem_new(struct drm_device *dev, uint64_t size, uint32_t flags, + uint32_t tile_flags, uint32_t cookie, uint32_t *user) +{ + int i; + struct drm_gem_object *obj; + struct pscnv_bo *vo; + + vo = pscnv_mem_alloc(dev, size, flags, tile_flags, cookie); + if (!vo) + return 0; + + obj = drm_gem_object_alloc(dev, vo->size); + if (!obj) { + pscnv_mem_free(vo); + return 0; + } +#ifndef PSCNV_KAPI_DRM_GEM_OBJECT_HANDLE_COUNT + atomic_inc(&obj->handle_count); +#endif + obj->driver_private = vo; + vo->gem = obj; + + if (user) + for (i = 0; i < ARRAY_SIZE(vo->user); i++) + vo->user[i] = user[i]; + else + for (i = 0; i < ARRAY_SIZE(vo->user); i++) + vo->user[i] = 0; + + return obj; +} diff --git a/driver/pscnv/pscnv_gem.h b/driver/pscnv/pscnv_gem.h new file mode 100644 index 00000000..34538e22 --- /dev/null +++ b/driver/pscnv/pscnv_gem.h @@ -0,0 +1,37 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#ifndef __PSCNV_GEM_H__ +#define __PSCNV_GEM_H__ + +#include "drmP.h" + +void pscnv_gem_free_object (struct drm_gem_object *); +struct drm_gem_object *pscnv_gem_new(struct drm_device *dev, uint64_t size, + uint32_t flags, uint32_t tile_flags, uint32_t cookie, + uint32_t *user); + +#endif diff --git a/driver/pscnv/pscnv_ioctl.c b/driver/pscnv/pscnv_ioctl.c new file mode 100644 index 00000000..b8c1760b --- /dev/null +++ b/driver/pscnv/pscnv_ioctl.c @@ -0,0 +1,500 @@ +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "nouveau_reg.h" +#include "pscnv_ioctl.h" +#include "pscnv_vm.h" +#include "pscnv_chan.h" +#include "pscnv_fifo.h" +#include "pscnv_gem.h" +#include "nv50_chan.h" +#include "nvc0_graph.h" +#include "pscnv_kapi.h" + +#ifdef PSCNV_KAPI_GETPARAM_BUS_TYPE +#define DEVICE_IS_AGP(dev) drm_device_is_agp(dev) +#define DEVICE_IS_PCIE(dev) drm_device_is_pcie(dev) +#else +#define DEVICE_IS_AGP(dev) drm_pci_device_is_agp(dev) +#define DEVICE_IS_PCIE(dev) pci_is_pcie(dev->pdev) +#endif + +int pscnv_ioctl_getparam(struct drm_device *dev, void *data, + struct drm_file *file_priv) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct drm_pscnv_getparam *getparam = data; + struct nvc0_graph_engine *nvc0_graph; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + switch (getparam->param) { + case PSCNV_GETPARAM_MP_COUNT: + if (dev_priv->chipset < 0xc0) + goto fail; + nvc0_graph = NVC0_GRAPH(dev_priv->engines[PSCNV_ENGINE_GRAPH]); + getparam->value = nvc0_graph->tp_count; /* MPs == TPs */ + break; + case PSCNV_GETPARAM_CHIPSET_ID: + getparam->value = dev_priv->chipset; + break; + case PSCNV_GETPARAM_PCI_VENDOR: + getparam->value = dev->pci_vendor; + break; + case PSCNV_GETPARAM_PCI_DEVICE: + getparam->value = dev->pci_device; + break; + case PSCNV_GETPARAM_BUS_TYPE: + if (DEVICE_IS_AGP(dev)) + getparam->value = NV_AGP; + else if (DEVICE_IS_PCIE(dev)) + getparam->value = NV_PCIE; + else + getparam->value = NV_PCI; + break; + case PSCNV_GETPARAM_PTIMER_TIME: + getparam->value = nv04_timer_read(dev); + break; + case PSCNV_GETPARAM_FB_SIZE: + getparam->value = dev_priv->vram_size; + break; + case PSCNV_GETPARAM_GRAPH_UNITS: + /* NV40 and NV50 versions are quite different, but register + * address is the same. User is supposed to know the card + * family anyway... */ + if (dev_priv->card_type >= NV_40 && dev_priv->card_type < NV_C0) { + getparam->value = nv_rd32(dev, NV40_PMC_GRAPH_UNITS); + break; + } + /* FALLTHRU */ + default: + goto fail; + } + + return 0; +fail: + NV_ERROR(dev, "unknown parameter %lld\n", getparam->param); + return -EINVAL; +} + +int pscnv_ioctl_gem_new(struct drm_device *dev, void *data, + struct drm_file *file_priv) +{ + struct drm_pscnv_gem_info *info = data; + struct drm_gem_object *obj; + struct pscnv_bo *bo; + int ret; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + obj = pscnv_gem_new(dev, info->size, info->flags, info->tile_flags, info->cookie, info->user); + if (!obj) { + return -ENOMEM; + } + bo = obj->driver_private; + + /* could change due to page size align */ + info->size = bo->size; + + ret = drm_gem_handle_create(file_priv, obj, &info->handle); + + if (pscnv_gem_debug >= 1) + NV_INFO(dev, "GEM handle %x is VO %x/%d\n", info->handle, bo->cookie, bo->serial); + + info->map_handle = (uint64_t)info->handle << 32; + drm_gem_object_handle_unreference_unlocked (obj); + return ret; +} + +int pscnv_ioctl_gem_info(struct drm_device *dev, void *data, + struct drm_file *file_priv) +{ + struct drm_pscnv_gem_info *info = data; + struct drm_gem_object *obj; + struct pscnv_bo *bo; + int i; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + obj = drm_gem_object_lookup(dev, file_priv, info->handle); + if (!obj) + return -EBADF; + + bo = obj->driver_private; + + info->cookie = bo->cookie; + info->flags = bo->flags; + info->tile_flags = bo->tile_flags; + info->size = obj->size; + info->map_handle = (uint64_t)info->handle << 32; + for (i = 0; i < ARRAY_SIZE(bo->user); i++) + info->user[i] = bo->user[i]; + + drm_gem_object_unreference_unlocked(obj); + + return 0; +} + +struct pscnv_vspace * +pscnv_get_vspace(struct drm_device *dev, struct drm_file *file_priv, int vid) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + unsigned long flags; + spin_lock_irqsave(&dev_priv->vm->vs_lock, flags); + + if (vid < 128 && vid >= 0 && dev_priv->vm->vspaces[vid] && dev_priv->vm->vspaces[vid]->filp == file_priv) { + struct pscnv_vspace *res = dev_priv->vm->vspaces[vid]; + pscnv_vspace_ref(res); + spin_unlock_irqrestore(&dev_priv->vm->vs_lock, flags); + return res; + } + spin_unlock_irqrestore(&dev_priv->vm->vs_lock, flags); + return 0; +} + +int pscnv_ioctl_vspace_new(struct drm_device *dev, void *data, + struct drm_file *file_priv) +{ + struct drm_pscnv_vspace_req *req = data; + struct pscnv_vspace *vs; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + vs = pscnv_vspace_new(dev, 1ull << 40, 0, 0); + if (!vs) + return -ENOMEM; + + req->vid = vs->vid; + + vs->filp = file_priv; + + return 0; +} + +int pscnv_ioctl_vspace_free(struct drm_device *dev, void *data, + struct drm_file *file_priv) +{ + struct drm_pscnv_vspace_req *req = data; + int vid = req->vid; + struct pscnv_vspace *vs; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + vs = pscnv_get_vspace(dev, file_priv, vid); + if (!vs) + return -ENOENT; + + vs->filp = 0; + pscnv_vspace_unref(vs); + pscnv_vspace_unref(vs); + + return 0; +} + +int pscnv_ioctl_vspace_map(struct drm_device *dev, void *data, + struct drm_file *file_priv) +{ + struct drm_pscnv_vspace_map *req = data; + struct pscnv_vspace *vs; + struct drm_gem_object *obj; + struct pscnv_bo *bo; + struct pscnv_mm_node *map; + int ret; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + vs = pscnv_get_vspace(dev, file_priv, req->vid); + if (!vs) + return -ENOENT; + + obj = drm_gem_object_lookup(dev, file_priv, req->handle); + if (!obj) { + pscnv_vspace_unref(vs); + return -EBADF; + } + + bo = obj->driver_private; + + ret = pscnv_vspace_map(vs, bo, req->start, req->end, req->back, &map); + if (!ret) + req->offset = map->start; + + pscnv_vspace_unref(vs); + + return ret; +} + +int pscnv_ioctl_vspace_unmap(struct drm_device *dev, void *data, + struct drm_file *file_priv) +{ + struct drm_pscnv_vspace_unmap *req = data; + struct pscnv_vspace *vs; + int ret; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + + vs = pscnv_get_vspace(dev, file_priv, req->vid); + if (!vs) + return -ENOENT; + + ret = pscnv_vspace_unmap(vs, req->offset); + + pscnv_vspace_unref(vs); + + return ret; +} + +void pscnv_vspace_cleanup(struct drm_device *dev, struct drm_file *file_priv) { + int vid; + struct pscnv_vspace *vs; + + for (vid = 0; vid < 128; vid++) { + vs = pscnv_get_vspace(dev, file_priv, vid); + if (!vs) + continue; + vs->filp = 0; + pscnv_vspace_unref(vs); + pscnv_vspace_unref(vs); + } +} + +struct pscnv_chan * +pscnv_get_chan(struct drm_device *dev, struct drm_file *file_priv, int cid) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + unsigned long flags; + spin_lock_irqsave(&dev_priv->chan->ch_lock, flags); + + if (cid < 128 && cid >= 0 && dev_priv->chan->chans[cid] && dev_priv->chan->chans[cid]->filp == file_priv) { + struct pscnv_chan *res = dev_priv->chan->chans[cid]; + pscnv_chan_ref(res); + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + return res; + } + spin_unlock_irqrestore(&dev_priv->chan->ch_lock, flags); + return 0; +} + +int pscnv_ioctl_chan_new(struct drm_device *dev, void *data, + struct drm_file *file_priv) +{ + struct drm_pscnv_chan_new *req = data; + struct pscnv_vspace *vs; + struct pscnv_chan *ch; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + vs = pscnv_get_vspace(dev, file_priv, req->vid); + if (!vs) + return -ENOENT; + + ch = pscnv_chan_new(dev, vs, 0); + if (!ch) { + pscnv_vspace_unref(vs); + return -ENOMEM; + } + pscnv_vspace_unref(vs); + + req->cid = ch->cid; + req->map_handle = 0xc0000000 | ch->cid << 16; + + ch->filp = file_priv; + + return 0; +} + +int pscnv_ioctl_chan_free(struct drm_device *dev, void *data, + struct drm_file *file_priv) +{ + struct drm_pscnv_chan_free *req = data; + struct pscnv_chan *ch; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + ch = pscnv_get_chan(dev, file_priv, req->cid); + if (!ch) + return -ENOENT; + + ch->filp = 0; + pscnv_chan_unref(ch); + pscnv_chan_unref(ch); + + return 0; +} + +int pscnv_ioctl_obj_vdma_new(struct drm_device *dev, void *data, + struct drm_file *file_priv) { + struct drm_pscnv_obj_vdma_new *req = data; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct pscnv_chan *ch; + int ret; + uint32_t oclass, inst; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + if (dev_priv->card_type != NV_50) + return -ENOSYS; + + oclass = req->oclass; + + if (oclass != 2 && oclass != 3 && oclass != 0x3d) + return -EINVAL; + + ch = pscnv_get_chan(dev, file_priv, req->cid); + if (!ch) + return -ENOENT; + + inst = nv50_chan_dmaobj_new(ch, 0x7fc00000 | oclass, req->start, req->size); + if (!inst) { + pscnv_chan_unref(ch); + return -ENOMEM; + } + + ret = pscnv_ramht_insert (&ch->ramht, req->handle, inst >> 4); + + pscnv_chan_unref(ch); + + return ret; +} + +void pscnv_chan_cleanup(struct drm_device *dev, struct drm_file *file_priv) { + int cid; + struct pscnv_chan *ch; + + for (cid = 0; cid < 128; cid++) { + ch = pscnv_get_chan(dev, file_priv, cid); + if (!ch) + continue; + ch->filp = 0; + pscnv_chan_unref(ch); + pscnv_chan_unref(ch); + } +} + +int pscnv_ioctl_obj_eng_new(struct drm_device *dev, void *data, + struct drm_file *file_priv) { + struct drm_pscnv_obj_eng_new *req = data; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct pscnv_chan *ch; + int ret; + int i; + uint32_t oclass = req->oclass; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + for (i = 0; i < PSCNV_ENGINES_NUM; i++) + if (dev_priv->engines[i]) { + uint32_t *pclass = dev_priv->engines[i]->oclasses; + if (!pclass) + continue; + while (*pclass) { + if (*pclass == oclass) + goto found; + pclass++; + } + } + return -ENODEV; + +found: + ch = pscnv_get_chan(dev, file_priv, req->cid); + if (!ch) + return -ENOENT; + + if (!ch->engdata[i]) { + ret = dev_priv->engines[i]->chan_alloc(dev_priv->engines[i], ch); + if (ret) { + pscnv_chan_unref(ch); + return ret; + } + } + + ret = dev_priv->engines[i]->chan_obj_new(dev_priv->engines[i], ch, req->handle, oclass, req->flags); + + pscnv_chan_unref(ch); + return ret; +} + +int pscnv_ioctl_fifo_init(struct drm_device *dev, void *data, + struct drm_file *file_priv) { + struct drm_pscnv_fifo_init *req = data; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct pscnv_chan *ch; + int ret; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + if (!dev_priv->fifo || !dev_priv->fifo->chan_init_dma) + return -ENODEV; + + ch = pscnv_get_chan(dev, file_priv, req->cid); + if (!ch) + return -ENOENT; + + ret = dev_priv->fifo->chan_init_dma(ch, req->pb_handle, req->flags, req->slimask, req->pb_start); + + pscnv_chan_unref(ch); + + return ret; +} + +int pscnv_ioctl_fifo_init_ib(struct drm_device *dev, void *data, + struct drm_file *file_priv) { + struct drm_pscnv_fifo_init_ib *req = data; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct pscnv_chan *ch; + int ret; + + NOUVEAU_CHECK_INITIALISED_WITH_RETURN; + + if (!dev_priv->fifo || !dev_priv->fifo->chan_init_ib) + return -ENODEV; + + ch = pscnv_get_chan(dev, file_priv, req->cid); + if (!ch) + return -ENOENT; + + ret = dev_priv->fifo->chan_init_ib(ch, req->pb_handle, req->flags, req->slimask, req->ib_start, req->ib_order); + + pscnv_chan_unref(ch); + + return ret; +} + +#ifdef PSCNV_KAPI_DRM_IOCTL_DEF_DRV +struct drm_ioctl_desc nouveau_ioctls[] = { + DRM_IOCTL_DEF_DRV(PSCNV_GETPARAM, pscnv_ioctl_getparam, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_GEM_NEW, pscnv_ioctl_gem_new, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_GEM_INFO, pscnv_ioctl_gem_info, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_VSPACE_NEW, pscnv_ioctl_vspace_new, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_VSPACE_FREE, pscnv_ioctl_vspace_free, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_VSPACE_MAP, pscnv_ioctl_vspace_map, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_VSPACE_UNMAP, pscnv_ioctl_vspace_unmap, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_CHAN_NEW, pscnv_ioctl_chan_new, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_CHAN_FREE, pscnv_ioctl_chan_free, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_OBJ_VDMA_NEW, pscnv_ioctl_obj_vdma_new, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_FIFO_INIT, pscnv_ioctl_fifo_init, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_OBJ_ENG_NEW, pscnv_ioctl_obj_eng_new, DRM_UNLOCKED), + DRM_IOCTL_DEF_DRV(PSCNV_FIFO_INIT_IB, pscnv_ioctl_fifo_init_ib, DRM_UNLOCKED), +}; +#elif defined(PSCNV_KAPI_DRM_IOCTL_DEF) +struct drm_ioctl_desc nouveau_ioctls[] = { + DRM_IOCTL_DEF(DRM_PSCNV_GETPARAM, pscnv_ioctl_getparam, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_GEM_NEW, pscnv_ioctl_gem_new, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_GEM_INFO, pscnv_ioctl_gem_info, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_VSPACE_NEW, pscnv_ioctl_vspace_new, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_VSPACE_FREE, pscnv_ioctl_vspace_free, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_VSPACE_MAP, pscnv_ioctl_vspace_map, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_VSPACE_UNMAP, pscnv_ioctl_vspace_unmap, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_CHAN_NEW, pscnv_ioctl_chan_new, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_CHAN_FREE, pscnv_ioctl_chan_free, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_OBJ_VDMA_NEW, pscnv_ioctl_obj_vdma_new, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_FIFO_INIT, pscnv_ioctl_fifo_init, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_OBJ_ENG_NEW, pscnv_ioctl_obj_eng_new, DRM_UNLOCKED), + DRM_IOCTL_DEF(DRM_PSCNV_FIFO_INIT_IB, pscnv_ioctl_fifo_init_ib, DRM_UNLOCKED), +}; +#else +#error "Unknown IOCTLDEF method." +#endif + +int nouveau_max_ioctl = DRM_ARRAY_SIZE(nouveau_ioctls); diff --git a/driver/pscnv/pscnv_ioctl.h b/driver/pscnv/pscnv_ioctl.h new file mode 100644 index 00000000..0d821781 --- /dev/null +++ b/driver/pscnv/pscnv_ioctl.h @@ -0,0 +1,36 @@ +#ifndef __PSCNV_IOCTL_H__ +#define __PSCNV_IOCTL_H__ + +extern int pscnv_ioctl_getparam(struct drm_device *, void *data, + struct drm_file *); +int pscnv_ioctl_gem_new(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_gem_info(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_vspace_new(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_vspace_free(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_vspace_map(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_vspace_unmap(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_chan_new(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_chan_free(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_obj_vdma_new(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_obj_eng_new(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_fifo_init(struct drm_device *dev, void *data, + struct drm_file *file_priv); +int pscnv_ioctl_fifo_init_ib(struct drm_device *dev, void *data, + struct drm_file *file_priv); + +extern void pscnv_chan_cleanup(struct drm_device *dev, struct drm_file *file_priv); +extern void pscnv_vspace_cleanup(struct drm_device *dev, struct drm_file *file_priv); +/* XXX: nuke it from here */ +struct pscnv_chan *pscnv_get_chan(struct drm_device *dev, struct drm_file *file_priv, int cid); + +#endif diff --git a/driver/pscnv/pscnv_kapi.h b/driver/pscnv/pscnv_kapi.h new file mode 100644 index 00000000..e69de29b diff --git a/driver/pscnv/pscnv_mem.c b/driver/pscnv/pscnv_mem.c new file mode 100644 index 00000000..77f3c393 --- /dev/null +++ b/driver/pscnv/pscnv_mem.c @@ -0,0 +1,192 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "pscnv_mem.h" +#include "pscnv_vm.h" +#include +#include +#include + +int +pscnv_mem_init(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + int ret, dma_bits = 32; + spin_lock_init(&dev_priv->pramin_lock); + + if (dev_priv->card_type >= NV_50 && + pci_dma_supported(dev->pdev, DMA_BIT_MASK(40))) + dma_bits = 40; + + ret = pci_set_dma_mask(dev->pdev, DMA_BIT_MASK(dma_bits)); + if (ret) { + NV_ERROR(dev, "Error setting DMA mask: %d\n", ret); + return ret; + } + + mutex_init(&dev_priv->vram_mutex); + + switch (dev_priv->card_type) { + case NV_50: + ret = nv50_vram_init(dev); + break; + case NV_C0: + ret = nvc0_vram_init(dev); + break; + default: + NV_ERROR(dev, "No VRAM allocator for NV%02x!\n", dev_priv->chipset); + ret = -ENOSYS; + } + if (ret) + return ret; + + dev_priv->fb_mtrr = drm_mtrr_add(pci_resource_start(dev->pdev, 1), + pci_resource_len(dev->pdev, 1), + DRM_MTRR_WC); + + return 0; +} + +void +pscnv_mem_takedown(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + dev_priv->vram->takedown(dev); + + if (dev_priv->fb_mtrr >= 0) { + drm_mtrr_del(dev_priv->fb_mtrr, pci_resource_start(dev->pdev, 1), + pci_resource_len(dev->pdev, 1), DRM_MTRR_WC); + dev_priv->fb_mtrr = 0; + } +} + +struct pscnv_bo * +pscnv_mem_alloc(struct drm_device *dev, + uint64_t size, int flags, int tile_flags, uint32_t cookie) +{ + static int serial = 0; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct pscnv_bo *res; + int ret; + /* avoid all sorts of integer overflows possible otherwise. */ + if (size >= (1ULL << 40)) + return 0; + if (!size) + return 0; + + res = kzalloc (sizeof *res, GFP_KERNEL); + if (!res) + return 0; + size = ALIGN(size, PSCNV_MEM_PAGE_SIZE); + size = ALIGN(size, PAGE_SIZE); + res->dev = dev; + res->size = size; + res->flags = flags; + res->tile_flags = tile_flags; + res->cookie = cookie; + res->gem = 0; + + /* XXX: another mutex? */ + mutex_lock(&dev_priv->vram_mutex); + res->serial = serial++; + mutex_unlock(&dev_priv->vram_mutex); + + if (pscnv_mem_debug >= 1) + NV_INFO(dev, "Allocating %d, %#llx-byte %sBO of type %08x, tile_flags %x\n", res->serial, size, + (flags & PSCNV_GEM_CONTIG ? "contig " : ""), cookie, tile_flags); + switch (res->flags & PSCNV_GEM_MEMTYPE_MASK) { + case PSCNV_GEM_VRAM_SMALL: + case PSCNV_GEM_VRAM_LARGE: + ret = dev_priv->vram->alloc(res); + break; + case PSCNV_GEM_SYSRAM_SNOOP: + case PSCNV_GEM_SYSRAM_NOSNOOP: + if (dev_priv->vram->sysram_tiling_ok(res)) + ret = pscnv_sysram_alloc(res); + else + ret = -EINVAL; + break; + default: + ret = -ENOSYS; + } + if (ret) { + kfree(res); + return 0; + } + return res; +} + +int +pscnv_mem_free(struct pscnv_bo *bo) +{ + struct drm_nouveau_private *dev_priv = bo->dev->dev_private; + if (pscnv_mem_debug >= 1) + NV_INFO(bo->dev, "Freeing %d, %#llx-byte %sBO of type %08x, tile_flags %x\n", bo->serial, bo->size, + (bo->flags & PSCNV_GEM_CONTIG ? "contig " : ""), bo->cookie, bo->tile_flags); + if (dev_priv->vm_ok && bo->map1) + pscnv_vspace_unmap_node(bo->map1); + if (dev_priv->vm_ok && bo->map3) + pscnv_vspace_unmap_node(bo->map3); + switch (bo->flags & PSCNV_GEM_MEMTYPE_MASK) { + case PSCNV_GEM_VRAM_SMALL: + case PSCNV_GEM_VRAM_LARGE: + dev_priv->vram->free(bo); + break; + case PSCNV_GEM_SYSRAM_SNOOP: + case PSCNV_GEM_SYSRAM_NOSNOOP: + pscnv_sysram_free(bo); + break; + } + kfree (bo); + return 0; +} + +int +pscnv_vram_free(struct pscnv_bo *bo) +{ + struct drm_nouveau_private *dev_priv = bo->dev->dev_private; + mutex_lock(&dev_priv->vram_mutex); + pscnv_mm_free(bo->mmnode); + mutex_unlock(&dev_priv->vram_mutex); + return 0; +} + +static void pscnv_vram_takedown_free(struct pscnv_mm_node *node) { + struct pscnv_bo *bo = node->tag; + NV_ERROR(bo->dev, "BO %d of type %08x still exists at takedown!\n", + bo->serial, bo->cookie); + pscnv_mem_free(bo); +} + +void +pscnv_vram_takedown(struct drm_device *dev) +{ + struct drm_nouveau_private *dev_priv = dev->dev_private; + pscnv_mm_takedown(dev_priv->vram_mm, pscnv_vram_takedown_free); +} diff --git a/driver/pscnv/pscnv_mem.h b/driver/pscnv/pscnv_mem.h new file mode 100644 index 00000000..e1654d5b --- /dev/null +++ b/driver/pscnv/pscnv_mem.h @@ -0,0 +1,85 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#ifndef __PSCNV_VRAM_H__ +#define __PSCNV_VRAM_H__ +#include "pscnv_drm.h" +#include "pscnv_mm.h" + +#define PSCNV_MEM_PAGE_SIZE 0x1000 + +/* A VRAM object of any kind. */ +struct pscnv_bo { + struct drm_device *dev; + /* size. Always a multiple of page size. */ + uint64_t size; + /* misc flags, see below. */ + int flags; + int tile_flags; + /* cookie: free-form 32-bit number displayed in debug info. */ + uint32_t cookie; + /* only used for debug */ + int serial; + /* only for contig blocks. same info as start of first [and only] + * region, but more convenient to access */ + uint64_t start; + /* the following used for GEM objects only */ + uint32_t user[8]; + struct drm_gem_object *gem; + struct pscnv_mm_node *map1; + struct pscnv_mm_node *map3; + /* VRAM only: the first mm node */ + struct pscnv_mm_node *mmnode; + /* SYSRaM only: list of pages */ + struct page **pages; + dma_addr_t *dmapages; +}; +#define PSCNV_GEM_NOUSER 0x10 + +struct pscnv_vram_engine { + void (*takedown) (struct drm_device *); + int (*alloc) (struct pscnv_bo *); + int (*free) (struct pscnv_bo *); + int (*sysram_tiling_ok) (struct pscnv_bo *); +}; + +extern int pscnv_mem_init(struct drm_device *); +extern void pscnv_mem_takedown(struct drm_device *); +extern struct pscnv_bo *pscnv_mem_alloc(struct drm_device *, + uint64_t size, int flags, int tile_flags, uint32_t cookie); +extern int pscnv_mem_free(struct pscnv_bo *); + +extern int pscnv_vram_free(struct pscnv_bo *bo); +extern void pscnv_vram_takedown(struct drm_device *dev); + +extern int nv50_vram_init(struct drm_device *); +extern int nvc0_vram_init(struct drm_device *); + +extern int pscnv_sysram_alloc(struct pscnv_bo *); +extern int pscnv_sysram_free(struct pscnv_bo *); +extern int pscnv_sysram_vm_fault(struct vm_area_struct *vma, struct vm_fault *vmf); + +#endif diff --git a/driver/pscnv/pscnv_mm.c b/driver/pscnv/pscnv_mm.c new file mode 100644 index 00000000..6b10f4b9 --- /dev/null +++ b/driver/pscnv/pscnv_mm.c @@ -0,0 +1,321 @@ +#include "pscnv_mm.h" +#include "nouveau_drv.h" +#include + +#undef PSCNV_RB_AUGMENT + +#define GTYPES 4 +#define TMASK 3 +#define LTMASK 1 + +static inline uint64_t +pscnv_rounddown (uint64_t x, uint32_t y) +{ + do_div(x, y); + x *= y; + return x; +} + +static inline uint64_t +pscnv_roundup (uint64_t x, uint32_t y) +{ + return pscnv_rounddown(x + y - 1, y); +} + +static void PSCNV_RB_AUGMENT(struct pscnv_mm_node *node) { + int i; + struct pscnv_mm_node *left = PSCNV_RB_LEFT(node, entry); + struct pscnv_mm_node *right = PSCNV_RB_RIGHT(node, entry); + for (i = 0; i < GTYPES; i++) { + node->maxgap[i] = node->gap[i]; + if (left && left->maxgap[i] > node->maxgap[i]) + node->maxgap[i] = left->maxgap[i]; + if (right && right->maxgap[i] > node->maxgap[i]) + node->maxgap[i] = right->maxgap[i]; + } +} + +static int nodecmp(struct pscnv_mm_node *a, struct pscnv_mm_node *b) { + if (a->sentinel < b->sentinel) + return -1; + else if (a->sentinel > b->sentinel) + return 1; + if (a->start < b->start) + return -1; + else if (a->start > b->start) + return 1; + return 0; +} + +PSCNV_RB_GENERATE_STATIC(pscnv_mm_head, pscnv_mm_node, entry, nodecmp) + +static void pscnv_mm_getfree(struct pscnv_mm_node *node, int type, uint64_t *start, uint64_t *end) { + uint64_t s = node->start, e = node->start + node->size; + struct pscnv_mm_node *prev = PSCNV_RB_PREV(pscnv_mm_head, entry, node); + struct pscnv_mm_node *next = PSCNV_RB_NEXT(pscnv_mm_head, entry, node); + if (prev->type != (type & LTMASK)) + s = pscnv_roundup(s, node->mm->tssize); + if (next->type != (type & LTMASK)) + e = pscnv_rounddown(e, node->mm->tssize); + if (type & PSCNV_MM_LP) { + s = pscnv_roundup(s, node->mm->lpsize); + e = pscnv_rounddown(e, node->mm->lpsize); + } else { + s = pscnv_roundup(s, node->mm->spsize); + e = pscnv_rounddown(e, node->mm->spsize); + } + if (e < s) + e = s; + *start = s; + *end = e; +} + +static void pscnv_mm_augup(struct pscnv_mm_node *node) { + struct pscnv_mm_node *n; + for (n = node; n; n = PSCNV_RB_PARENT(n, entry)) + PSCNV_RB_AUGMENT(n); +} + +static void pscnv_mm_free_node(struct pscnv_mm_node *node) { + struct pscnv_mm_node *prev = PSCNV_RB_PREV(pscnv_mm_head, entry, node); + struct pscnv_mm_node *next = PSCNV_RB_NEXT(pscnv_mm_head, entry, node); + int i; + if (pscnv_mm_debug >= 2) + NV_INFO(node->mm->dev, "MM: Freeing node %llx..%llx of type %d\n", node->start, node->start + node->size, node->type); + node->type = PSCNV_MM_TYPE_FREE; + if (prev->type == PSCNV_MM_TYPE_FREE) { + if (pscnv_mm_debug >= 2) + NV_INFO(node->mm->dev, "MM: Merging left with node %llx..%llx\n", prev->start, prev->start + prev->size); + BUG_ON(prev->start + prev->size != node->start); + node->start = prev->start; + node->size += prev->size; + PSCNV_RB_REMOVE(pscnv_mm_head, &node->mm->head, prev); + kfree(prev); + } + if (next->type == PSCNV_MM_TYPE_FREE) { + if (pscnv_mm_debug >= 2) + NV_INFO(node->mm->dev, "MM: Merging right with node %llx..%llx\n", next->start, next->start + next->size); + BUG_ON(node->start + node->size != next->start); + node->size += next->size; + PSCNV_RB_REMOVE(pscnv_mm_head, &node->mm->head, next); + kfree(next); + } + for (i = 0; i < GTYPES; i++) { + uint64_t s, e; + pscnv_mm_getfree(node, i, &s, &e); + node->gap[i] = e - s; + } + pscnv_mm_augup(node); +} + +void pscnv_mm_free(struct pscnv_mm_node *node) { + while (node->prev) + node = node->prev; + while (node) { + struct pscnv_mm_node *next = node->next; + pscnv_mm_free_node(node); + node = next; + } +} + +int pscnv_mm_init(struct drm_device *dev, uint64_t start, uint64_t end, uint32_t spsize, uint32_t lpsize, uint32_t tssize, struct pscnv_mm **res) { + struct pscnv_mm *mm = kzalloc(sizeof *mm, GFP_KERNEL); + struct pscnv_mm_node *ss, *se, *node; + if (!mm) + return -ENOMEM; + if (!(ss = kzalloc(sizeof *ss, GFP_KERNEL))) { + kfree(mm); + return -ENOMEM; + } + if (!(se = kzalloc(sizeof *se, GFP_KERNEL))) { + kfree(ss); + kfree(mm); + return -ENOMEM; + } + if (!(node = kzalloc(sizeof *node, GFP_KERNEL))) { + kfree(se); + kfree(ss); + kfree(mm); + return -ENOMEM; + } + mm->dev = dev; + mm->spsize = spsize; + mm->lpsize = lpsize; + mm->tssize = tssize; + ss->type = se->type = PSCNV_MM_TYPE_USED0; + ss->sentinel = -1; + se->sentinel = 1; + ss->start = start; + se->start = end; + node->start = start; + node->size = end - start; + node->mm = ss->mm = se->mm = mm; + PSCNV_RB_INSERT(pscnv_mm_head, &mm->head, ss); + PSCNV_RB_INSERT(pscnv_mm_head, &mm->head, node); + PSCNV_RB_INSERT(pscnv_mm_head, &mm->head, se); + pscnv_mm_free_node(node); + *res = mm; + return 0; +} + +void pscnv_mm_takedown(struct pscnv_mm *mm, void (*free_callback)(struct pscnv_mm_node *)) { + struct pscnv_mm_node *cur; +restart: + cur = PSCNV_RB_MIN(pscnv_mm_head, &mm->head); + cur = PSCNV_RB_NEXT(pscnv_mm_head, entry, cur); + while (cur->type == PSCNV_MM_TYPE_FREE) + cur = PSCNV_RB_NEXT(pscnv_mm_head, entry, cur); + if (!cur->sentinel) { + while (cur->prev) + cur = cur->prev; + if (pscnv_mm_debug >= 1) + NV_INFO (mm->dev, "MM: takedown free %llx..%llx type %d\n", cur->start, cur->start + cur->size, cur->type); + free_callback(cur); + goto restart; + } + while ((cur = PSCNV_RB_ROOT(&mm->head))) { + PSCNV_RB_REMOVE(pscnv_mm_head, &mm->head, cur); + kfree(cur); + } + kfree(mm); +} + +static int pscnv_mm_alloc_single(struct pscnv_mm_node *node, uint64_t size, uint32_t flags, uint64_t start, uint64_t end, struct pscnv_mm_node **res) { + struct pscnv_mm_node *left = PSCNV_RB_LEFT(node, entry), *right = PSCNV_RB_RIGHT(node, entry); + uint64_t minsz = ((flags & PSCNV_MM_FRAGOK) ? 1 : size); + int lok = left && left->maxgap[flags & TMASK] >= minsz && node->start > start; + int rok = right && right->maxgap[flags & TMASK] >= minsz && node->start + node->size < end; + int back = flags & PSCNV_MM_FROMBACK; + uint64_t s, e; + struct pscnv_mm_node *lsp = 0, *rsp = 0; + int i; + + if (!back && lok && !pscnv_mm_alloc_single(left, size, flags, start, end, res)) + return 0; + if (back && rok && !pscnv_mm_alloc_single(right, size, flags, start, end, res)) + return 0; + + if (node->type == PSCNV_MM_TYPE_FREE) { + pscnv_mm_getfree(node, flags & TMASK, &s, &e); + if (start > s) + s = start; + if (end < e) + e = end; + if (e < s) + e = s; + if (e-s >= minsz) { + if (pscnv_mm_debug >= 2) + NV_INFO(node->mm->dev, "MM: Using node %llx..%llx, space %llx..%llx\n", node->start, node->start + node->size, s, e); + if (e-s > size) { + if (back) + s = e - size; + else + e = s + size; + } + + if (s != node->start) { + lsp = kzalloc(sizeof *lsp, GFP_KERNEL); + if (!lsp) + return -ENOMEM; + } + if (e != node->start + node->size) { + rsp = kzalloc(sizeof *rsp, GFP_KERNEL); + if (!rsp) { + if (lsp) + kfree(lsp); + return -ENOMEM; + } + } + + node->type = flags & LTMASK; + for (i = 0; i < GTYPES; i++) + node->gap[i] = 0; + pscnv_mm_augup(node); + + if (lsp) { + lsp->mm = node->mm; + lsp->start = node->start; + lsp->size = s - node->start; + node->size -= lsp->size; + node->start = s; + PSCNV_RB_INSERT(pscnv_mm_head, &node->mm->head, lsp); + pscnv_mm_free_node(lsp); + } + + if (rsp) { + rsp->mm = node->mm; + rsp->start = e; + rsp->size = node->start + node->size - e; + node->size -= rsp->size; + PSCNV_RB_INSERT(pscnv_mm_head, &node->mm->head, rsp); + pscnv_mm_free_node(rsp); + } + if (pscnv_mm_debug >= 2) + NV_INFO(node->mm->dev, "MM: After split: %llx..%llx\n", node->start, node->start + node->size); + + *res = node; + return 0; + } + } + + if (back && lok && !pscnv_mm_alloc_single(left, size, flags, start, end, res)) + return 0; + if (!back && rok && !pscnv_mm_alloc_single(right, size, flags, start, end, res)) + return 0; + return -ENOMEM; +} + +int pscnv_mm_alloc(struct pscnv_mm *mm, uint64_t size, uint32_t flags, uint64_t start, uint64_t end, struct pscnv_mm_node **res) { + uint32_t psize; + struct pscnv_mm_node *last = 0; + int ret; + if (flags & PSCNV_MM_LP) + psize = mm->lpsize; + else + psize = mm->spsize; + size = pscnv_roundup(size, psize); + start = pscnv_roundup(start, psize); + end = pscnv_rounddown(end, psize); + /* avoid various bounduary conditions */ + if (size > (1ull << 60)) + return -EINVAL; + if (pscnv_mm_debug >= 1) + NV_INFO(mm->dev, "MM: Allocation size %llx at %llx..%llx flags %d\n", size, start, end, flags); + while (size) { + struct pscnv_mm_node *cur; + ret = pscnv_mm_alloc_single(PSCNV_RB_ROOT(&mm->head), size, flags, start, end, &cur); + if (ret) { + while (last) { + cur = last->prev; + pscnv_mm_free_node(last); + last = cur; + } + return ret; + } + size -= cur->size; + if (last) { + last->next = cur; + cur->prev = last; + last = cur; + } else { + *res = last = cur; + cur->prev = 0; + } + } + if (last) + last->next = 0; + return 0; +} + +struct pscnv_mm_node *pscnv_mm_find_node(struct pscnv_mm *mm, uint64_t addr) { + struct pscnv_mm_node *node = PSCNV_RB_ROOT(&mm->head); + while (node) { + if (addr < node->start) + node = PSCNV_RB_LEFT(node, entry); + else if (addr >= node->start + node->size) + node = PSCNV_RB_RIGHT(node, entry); + else + return node; + } + return 0; +} diff --git a/driver/pscnv/pscnv_mm.h b/driver/pscnv/pscnv_mm.h new file mode 100644 index 00000000..3ff90843 --- /dev/null +++ b/driver/pscnv/pscnv_mm.h @@ -0,0 +1,48 @@ +#ifndef PSCNV_MM_H +#define PSCNV_MM_H + +#include "drmP.h" +#include "drm.h" +#include "pscnv_tree.h" + +PSCNV_RB_HEAD(pscnv_mm_head, pscnv_mm_node); + +struct pscnv_mm { + struct drm_device *dev; + struct pscnv_mm_head head; + uint32_t spsize; + uint32_t lpsize; + uint32_t tssize; +}; + +struct pscnv_mm_node { + PSCNV_RB_ENTRY(pscnv_mm_node) entry; + struct pscnv_mm *mm; + uint64_t maxgap[4]; + uint64_t gap[4]; + int sentinel; + enum { + PSCNV_MM_TYPE_USED0, + PSCNV_MM_TYPE_USED1, + PSCNV_MM_TYPE_FREE, + } type; + uint64_t start; + uint64_t size; + struct pscnv_mm_node *next; + struct pscnv_mm_node *prev; + void *tag; + void *tag2; +}; + +#define PSCNV_MM_T1 1 +#define PSCNV_MM_LP 2 +#define PSCNV_MM_FRAGOK 4 +#define PSCNV_MM_FROMBACK 8 + +int pscnv_mm_init(struct drm_device *dev, uint64_t start, uint64_t end, uint32_t spsize, uint32_t lpsize, uint32_t tssize, struct pscnv_mm **res); +int pscnv_mm_alloc(struct pscnv_mm *mm, uint64_t size, uint32_t flags, uint64_t start, uint64_t end, struct pscnv_mm_node **res); +void pscnv_mm_free(struct pscnv_mm_node *node); +void pscnv_mm_takedown(struct pscnv_mm *mm, void (*free_callback)(struct pscnv_mm_node *)); +struct pscnv_mm_node *pscnv_mm_find_node(struct pscnv_mm *mm, uint64_t addr); + +#endif diff --git a/driver/pscnv/pscnv_ramht.c b/driver/pscnv/pscnv_ramht.c new file mode 100644 index 00000000..549a3fc9 --- /dev/null +++ b/driver/pscnv/pscnv_ramht.c @@ -0,0 +1,94 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drm.h" +#include "drmP.h" +#include "nouveau_drv.h" +#include "pscnv_ramht.h" +#include "pscnv_vm.h" + +uint32_t pscnv_ramht_hash(struct pscnv_ramht *ramht, uint32_t handle) { + uint32_t hash = 0; + while (handle) { + hash ^= handle & ((1 << ramht->bits) - 1); + handle >>= ramht->bits; + } + return hash; +} + +int pscnv_ramht_insert(struct pscnv_ramht *ramht, uint32_t handle, uint32_t context) { + /* XXX: check if the object exists already... */ + struct drm_nouveau_private *dev_priv = ramht->bo->dev->dev_private; + uint32_t hash = pscnv_ramht_hash(ramht, handle); + uint32_t start = hash * 8; + uint32_t pos = start; + if (pscnv_ramht_debug >= 2) + NV_INFO(ramht->bo->dev, "Handle %x hash %x\n", handle, hash); + spin_lock (&ramht->lock); + do { + if (!nv_rv32(ramht->bo, ramht->offset + pos + 4)) { + nv_wv32(ramht->bo, ramht->offset + pos, handle); + nv_wv32(ramht->bo, ramht->offset + pos + 4, context); + dev_priv->vm->bar_flush(ramht->bo->dev); + spin_unlock (&ramht->lock); + if (pscnv_ramht_debug >= 1) + NV_INFO(ramht->bo->dev, "Adding RAMHT entry for object %x at %x, context %x\n", handle, pos, context); + return 0; + } + pos += 8; + if (pos == 8 << ramht->bits) + pos = 0; + } while (pos != start); + spin_unlock (&ramht->lock); + NV_ERROR(ramht->bo->dev, "No RAMHT space for object %x\n", handle); + return -ENOMEM; +} + +uint32_t pscnv_ramht_find(struct pscnv_ramht *ramht, uint32_t handle) { + /* XXX: do this properly. */ + uint32_t hash = pscnv_ramht_hash(ramht, handle); + uint32_t start = hash * 8; + uint32_t pos = start; + uint32_t res; + if (pscnv_ramht_debug >= 2) + NV_INFO(ramht->bo->dev, "Handle %x hash %x\n", handle, hash); + spin_lock (&ramht->lock); + do { + if (!nv_rv32(ramht->bo, ramht->offset + pos + 4)) + break; + if (nv_rv32(ramht->bo, ramht->offset + pos) == handle) { + res = nv_rv32(ramht->bo, ramht->offset + pos + 4); + spin_unlock (&ramht->lock); + return res; + } + pos += 8; + if (pos == 8 << ramht->bits) + pos = 0; + } while (pos != start); + spin_unlock (&ramht->lock); + NV_ERROR(ramht->bo->dev, "RAMHT object %x not found\n", handle); + return 0; +} diff --git a/driver/pscnv/pscnv_ramht.h b/driver/pscnv/pscnv_ramht.h new file mode 100644 index 00000000..3c25187d --- /dev/null +++ b/driver/pscnv/pscnv_ramht.h @@ -0,0 +1,41 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#ifndef __PSCNV_RAMHT_H__ +#define __PSCNV_RAMHT_H__ + +struct pscnv_ramht { + struct pscnv_bo *bo; + spinlock_t lock; + uint32_t offset; + int bits; +}; + +extern uint32_t pscnv_ramht_hash(struct pscnv_ramht *, uint32_t handle); +extern int pscnv_ramht_insert(struct pscnv_ramht *, uint32_t handle, uint32_t context); +extern uint32_t pscnv_ramht_find(struct pscnv_ramht *, uint32_t handle); + +#endif diff --git a/driver/pscnv/pscnv_sysram.c b/driver/pscnv/pscnv_sysram.c new file mode 100644 index 00000000..a38eee62 --- /dev/null +++ b/driver/pscnv/pscnv_sysram.c @@ -0,0 +1,81 @@ +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "pscnv_mem.h" +#include +#include +#include +#include + +int +pscnv_sysram_alloc(struct pscnv_bo *bo) +{ + int numpages, i, j; + gfp_t gfp_flags; + numpages = bo->size >> PAGE_SHIFT; + if (numpages > 1 && bo->flags & PSCNV_GEM_CONTIG) + return -EINVAL; + bo->pages = kmalloc(numpages * sizeof *bo->pages, GFP_KERNEL); + if (!bo->pages) + return -ENOMEM; + bo->dmapages = kmalloc(numpages * sizeof *bo->dmapages, GFP_KERNEL); + if (!bo->dmapages) { + kfree(bo->pages); + return -ENOMEM; + } + if (bo->dev->pdev->dma_mask > 0xffffffff) + gfp_flags = GFP_KERNEL; + else + gfp_flags = GFP_DMA32; + for (i = 0; i < numpages; i++) { + bo->pages[i] = alloc_pages(gfp_flags, 0); + if (!bo->pages[i]) { + for (j = 0; j < i; j++) + put_page(bo->pages[j]); + kfree(bo->pages); + kfree(bo->dmapages); + return -ENOMEM; + } + } + for (i = 0; i < numpages; i++) { + bo->dmapages[i] = pci_map_page(bo->dev->pdev, bo->pages[i], 0, PAGE_SIZE, PCI_DMA_BIDIRECTIONAL); + if (pci_dma_mapping_error(bo->dev->pdev, bo->dmapages[i])) { + for (j = 0; j < i; j++) + pci_unmap_page(bo->dev->pdev, bo->dmapages[j], PAGE_SIZE, PCI_DMA_BIDIRECTIONAL); + for (j = 0; j < numpages; j++) + put_page(bo->pages[j]); + kfree(bo->pages); + kfree(bo->dmapages); + return -ENOMEM; + } + } + return 0; +} + +int +pscnv_sysram_free(struct pscnv_bo *bo) +{ + int numpages, i; + numpages = bo->size >> PAGE_SHIFT; + for (i = 0; i < numpages; i++) + pci_unmap_page(bo->dev->pdev, bo->dmapages[i], PAGE_SIZE, PCI_DMA_BIDIRECTIONAL); + for (i = 0; i < numpages; i++) + put_page(bo->pages[i]); + kfree(bo->pages); + kfree(bo->dmapages); + return 0; +} + +extern int pscnv_sysram_vm_fault(struct vm_area_struct *vma, struct vm_fault *vmf) +{ + struct drm_gem_object *obj = vma->vm_private_data; + struct pscnv_bo *bo = obj->driver_private; + uint64_t offset = (uint64_t)vmf->virtual_address - vma->vm_start; + struct page *res; + if (offset > bo->size) + return VM_FAULT_SIGBUS; + res = bo->pages[offset >> PAGE_SHIFT]; + get_page(res); + vmf->page = res; + return 0; +} diff --git a/driver/pscnv/pscnv_tree.h b/driver/pscnv/pscnv_tree.h new file mode 100644 index 00000000..691a0660 --- /dev/null +++ b/driver/pscnv/pscnv_tree.h @@ -0,0 +1,487 @@ +/* + * Originally sys/tree.h from FreeBSD. Changes: + * - SPLAY removed + * - name changed to avoid collisions + */ + +/* + * Copyright 2002 Niels Provos + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef __PSCNV_TREE_H__ +#define __PSCNV_TREE_H__ + +#define __unused __attribute__((__unused__)) + +/* Macros that define a red-black tree */ +#define PSCNV_RB_HEAD(name, type) \ +struct name { \ + struct type *rbh_root; /* root of the tree */ \ +} + +#define PSCNV_RB_INITIALIZER(root) \ + { NULL } + +#define PSCNV_RB_INIT(root) do { \ + (root)->rbh_root = NULL; \ +} while (/*CONSTCOND*/ 0) + +#define PSCNV_RB_BLACK 0 +#define PSCNV_RB_RED 1 +#define PSCNV_RB_ENTRY(type) \ +struct { \ + struct type *rbe_left; /* left element */ \ + struct type *rbe_right; /* right element */ \ + struct type *rbe_parent; /* parent element */ \ + int rbe_color; /* node color */ \ +} + +#define PSCNV_RB_LEFT(elm, field) (elm)->field.rbe_left +#define PSCNV_RB_RIGHT(elm, field) (elm)->field.rbe_right +#define PSCNV_RB_PARENT(elm, field) (elm)->field.rbe_parent +#define PSCNV_RB_COLOR(elm, field) (elm)->field.rbe_color +#define PSCNV_RB_ROOT(head) (head)->rbh_root +#define PSCNV_RB_EMPTY(head) (PSCNV_RB_ROOT(head) == NULL) + +#define PSCNV_RB_SET(elm, parent, field) do { \ + PSCNV_RB_PARENT(elm, field) = parent; \ + PSCNV_RB_LEFT(elm, field) = PSCNV_RB_RIGHT(elm, field) = NULL; \ + PSCNV_RB_COLOR(elm, field) = PSCNV_RB_RED; \ +} while (/*CONSTCOND*/ 0) + +#define PSCNV_RB_SET_BLACKRED(black, red, field) do { \ + PSCNV_RB_COLOR(black, field) = PSCNV_RB_BLACK; \ + PSCNV_RB_COLOR(red, field) = PSCNV_RB_RED; \ +} while (/*CONSTCOND*/ 0) + +#ifndef PSCNV_RB_AUGMENT +#define PSCNV_RB_AUGMENT(x) (void)(x) +#endif + +#define PSCNV_RB_ROTATE_LEFT(head, elm, tmp, field) do { \ + (tmp) = PSCNV_RB_RIGHT(elm, field); \ + if ((PSCNV_RB_RIGHT(elm, field) = PSCNV_RB_LEFT(tmp, field)) != NULL) { \ + PSCNV_RB_PARENT(PSCNV_RB_LEFT(tmp, field), field) = (elm); \ + } \ + PSCNV_RB_AUGMENT(elm); \ + if ((PSCNV_RB_PARENT(tmp, field) = PSCNV_RB_PARENT(elm, field)) != NULL) { \ + if ((elm) == PSCNV_RB_LEFT(PSCNV_RB_PARENT(elm, field), field)) \ + PSCNV_RB_LEFT(PSCNV_RB_PARENT(elm, field), field) = (tmp); \ + else \ + PSCNV_RB_RIGHT(PSCNV_RB_PARENT(elm, field), field) = (tmp); \ + } else \ + (head)->rbh_root = (tmp); \ + PSCNV_RB_LEFT(tmp, field) = (elm); \ + PSCNV_RB_PARENT(elm, field) = (tmp); \ + PSCNV_RB_AUGMENT(tmp); \ + if ((PSCNV_RB_PARENT(tmp, field))) \ + PSCNV_RB_AUGMENT(PSCNV_RB_PARENT(tmp, field)); \ +} while (/*CONSTCOND*/ 0) + +#define PSCNV_RB_ROTATE_RIGHT(head, elm, tmp, field) do { \ + (tmp) = PSCNV_RB_LEFT(elm, field); \ + if ((PSCNV_RB_LEFT(elm, field) = PSCNV_RB_RIGHT(tmp, field)) != NULL) { \ + PSCNV_RB_PARENT(PSCNV_RB_RIGHT(tmp, field), field) = (elm); \ + } \ + PSCNV_RB_AUGMENT(elm); \ + if ((PSCNV_RB_PARENT(tmp, field) = PSCNV_RB_PARENT(elm, field)) != NULL) { \ + if ((elm) == PSCNV_RB_LEFT(PSCNV_RB_PARENT(elm, field), field)) \ + PSCNV_RB_LEFT(PSCNV_RB_PARENT(elm, field), field) = (tmp); \ + else \ + PSCNV_RB_RIGHT(PSCNV_RB_PARENT(elm, field), field) = (tmp); \ + } else \ + (head)->rbh_root = (tmp); \ + PSCNV_RB_RIGHT(tmp, field) = (elm); \ + PSCNV_RB_PARENT(elm, field) = (tmp); \ + PSCNV_RB_AUGMENT(tmp); \ + if ((PSCNV_RB_PARENT(tmp, field))) \ + PSCNV_RB_AUGMENT(PSCNV_RB_PARENT(tmp, field)); \ +} while (/*CONSTCOND*/ 0) + +/* Generates prototypes and inline functions */ +#define PSCNV_RB_PROTOTYPE(name, type, field, cmp) \ + PSCNV_RB_PROTOTYPE_INTERNAL(name, type, field, cmp,) +#define PSCNV_RB_PROTOTYPE_STATIC(name, type, field, cmp) \ + PSCNV_RB_PROTOTYPE_INTERNAL(name, type, field, cmp, __unused static) +#define PSCNV_RB_PROTOTYPE_INTERNAL(name, type, field, cmp, attr) \ +attr void name##_PSCNV_RB_INSERT_COLOR(struct name *, struct type *); \ +attr void name##_PSCNV_RB_REMOVE_COLOR(struct name *, struct type *, struct type *);\ +attr struct type *name##_PSCNV_RB_REMOVE(struct name *, struct type *); \ +attr struct type *name##_PSCNV_RB_INSERT(struct name *, struct type *); \ +attr struct type *name##_PSCNV_RB_FIND(struct name *, struct type *); \ +attr struct type *name##_PSCNV_RB_NFIND(struct name *, struct type *); \ +attr struct type *name##_PSCNV_RB_NEXT(struct type *); \ +attr struct type *name##_PSCNV_RB_PREV(struct type *); \ +attr struct type *name##_PSCNV_RB_MINMAX(struct name *, int); \ + \ + +/* Main rb operation. + * Moves node close to the key of elm to top + */ +#define PSCNV_RB_GENERATE(name, type, field, cmp) \ + PSCNV_RB_GENERATE_INTERNAL(name, type, field, cmp,) +#define PSCNV_RB_GENERATE_STATIC(name, type, field, cmp) \ + PSCNV_RB_GENERATE_INTERNAL(name, type, field, cmp, __unused static) +#define PSCNV_RB_GENERATE_INTERNAL(name, type, field, cmp, attr) \ +attr void \ +name##_PSCNV_RB_INSERT_COLOR(struct name *head, struct type *elm) \ +{ \ + struct type *parent, *gparent, *tmp; \ + while ((parent = PSCNV_RB_PARENT(elm, field)) != NULL && \ + PSCNV_RB_COLOR(parent, field) == PSCNV_RB_RED) { \ + gparent = PSCNV_RB_PARENT(parent, field); \ + if (parent == PSCNV_RB_LEFT(gparent, field)) { \ + tmp = PSCNV_RB_RIGHT(gparent, field); \ + if (tmp && PSCNV_RB_COLOR(tmp, field) == PSCNV_RB_RED) { \ + PSCNV_RB_COLOR(tmp, field) = PSCNV_RB_BLACK; \ + PSCNV_RB_SET_BLACKRED(parent, gparent, field);\ + elm = gparent; \ + continue; \ + } \ + if (PSCNV_RB_RIGHT(parent, field) == elm) { \ + PSCNV_RB_ROTATE_LEFT(head, parent, tmp, field);\ + tmp = parent; \ + parent = elm; \ + elm = tmp; \ + } \ + PSCNV_RB_SET_BLACKRED(parent, gparent, field); \ + PSCNV_RB_ROTATE_RIGHT(head, gparent, tmp, field); \ + } else { \ + tmp = PSCNV_RB_LEFT(gparent, field); \ + if (tmp && PSCNV_RB_COLOR(tmp, field) == PSCNV_RB_RED) { \ + PSCNV_RB_COLOR(tmp, field) = PSCNV_RB_BLACK; \ + PSCNV_RB_SET_BLACKRED(parent, gparent, field);\ + elm = gparent; \ + continue; \ + } \ + if (PSCNV_RB_LEFT(parent, field) == elm) { \ + PSCNV_RB_ROTATE_RIGHT(head, parent, tmp, field);\ + tmp = parent; \ + parent = elm; \ + elm = tmp; \ + } \ + PSCNV_RB_SET_BLACKRED(parent, gparent, field); \ + PSCNV_RB_ROTATE_LEFT(head, gparent, tmp, field); \ + } \ + } \ + PSCNV_RB_COLOR(head->rbh_root, field) = PSCNV_RB_BLACK; \ +} \ + \ +attr void \ +name##_PSCNV_RB_REMOVE_COLOR(struct name *head, struct type *parent, struct type *elm) \ +{ \ + struct type *tmp; \ + while ((elm == NULL || PSCNV_RB_COLOR(elm, field) == PSCNV_RB_BLACK) && \ + elm != PSCNV_RB_ROOT(head)) { \ + if (PSCNV_RB_LEFT(parent, field) == elm) { \ + tmp = PSCNV_RB_RIGHT(parent, field); \ + if (PSCNV_RB_COLOR(tmp, field) == PSCNV_RB_RED) { \ + PSCNV_RB_SET_BLACKRED(tmp, parent, field); \ + PSCNV_RB_ROTATE_LEFT(head, parent, tmp, field);\ + tmp = PSCNV_RB_RIGHT(parent, field); \ + } \ + if ((PSCNV_RB_LEFT(tmp, field) == NULL || \ + PSCNV_RB_COLOR(PSCNV_RB_LEFT(tmp, field), field) == PSCNV_RB_BLACK) &&\ + (PSCNV_RB_RIGHT(tmp, field) == NULL || \ + PSCNV_RB_COLOR(PSCNV_RB_RIGHT(tmp, field), field) == PSCNV_RB_BLACK)) {\ + PSCNV_RB_COLOR(tmp, field) = PSCNV_RB_RED; \ + elm = parent; \ + parent = PSCNV_RB_PARENT(elm, field); \ + } else { \ + if (PSCNV_RB_RIGHT(tmp, field) == NULL || \ + PSCNV_RB_COLOR(PSCNV_RB_RIGHT(tmp, field), field) == PSCNV_RB_BLACK) {\ + struct type *oleft; \ + if ((oleft = PSCNV_RB_LEFT(tmp, field)) \ + != NULL) \ + PSCNV_RB_COLOR(oleft, field) = PSCNV_RB_BLACK;\ + PSCNV_RB_COLOR(tmp, field) = PSCNV_RB_RED; \ + PSCNV_RB_ROTATE_RIGHT(head, tmp, oleft, field);\ + tmp = PSCNV_RB_RIGHT(parent, field); \ + } \ + PSCNV_RB_COLOR(tmp, field) = PSCNV_RB_COLOR(parent, field);\ + PSCNV_RB_COLOR(parent, field) = PSCNV_RB_BLACK; \ + if (PSCNV_RB_RIGHT(tmp, field)) \ + PSCNV_RB_COLOR(PSCNV_RB_RIGHT(tmp, field), field) = PSCNV_RB_BLACK;\ + PSCNV_RB_ROTATE_LEFT(head, parent, tmp, field);\ + elm = PSCNV_RB_ROOT(head); \ + break; \ + } \ + } else { \ + tmp = PSCNV_RB_LEFT(parent, field); \ + if (PSCNV_RB_COLOR(tmp, field) == PSCNV_RB_RED) { \ + PSCNV_RB_SET_BLACKRED(tmp, parent, field); \ + PSCNV_RB_ROTATE_RIGHT(head, parent, tmp, field);\ + tmp = PSCNV_RB_LEFT(parent, field); \ + } \ + if ((PSCNV_RB_LEFT(tmp, field) == NULL || \ + PSCNV_RB_COLOR(PSCNV_RB_LEFT(tmp, field), field) == PSCNV_RB_BLACK) &&\ + (PSCNV_RB_RIGHT(tmp, field) == NULL || \ + PSCNV_RB_COLOR(PSCNV_RB_RIGHT(tmp, field), field) == PSCNV_RB_BLACK)) {\ + PSCNV_RB_COLOR(tmp, field) = PSCNV_RB_RED; \ + elm = parent; \ + parent = PSCNV_RB_PARENT(elm, field); \ + } else { \ + if (PSCNV_RB_LEFT(tmp, field) == NULL || \ + PSCNV_RB_COLOR(PSCNV_RB_LEFT(tmp, field), field) == PSCNV_RB_BLACK) {\ + struct type *oright; \ + if ((oright = PSCNV_RB_RIGHT(tmp, field)) \ + != NULL) \ + PSCNV_RB_COLOR(oright, field) = PSCNV_RB_BLACK;\ + PSCNV_RB_COLOR(tmp, field) = PSCNV_RB_RED; \ + PSCNV_RB_ROTATE_LEFT(head, tmp, oright, field);\ + tmp = PSCNV_RB_LEFT(parent, field); \ + } \ + PSCNV_RB_COLOR(tmp, field) = PSCNV_RB_COLOR(parent, field);\ + PSCNV_RB_COLOR(parent, field) = PSCNV_RB_BLACK; \ + if (PSCNV_RB_LEFT(tmp, field)) \ + PSCNV_RB_COLOR(PSCNV_RB_LEFT(tmp, field), field) = PSCNV_RB_BLACK;\ + PSCNV_RB_ROTATE_RIGHT(head, parent, tmp, field);\ + elm = PSCNV_RB_ROOT(head); \ + break; \ + } \ + } \ + } \ + if (elm) \ + PSCNV_RB_COLOR(elm, field) = PSCNV_RB_BLACK; \ +} \ + \ +attr struct type * \ +name##_PSCNV_RB_REMOVE(struct name *head, struct type *elm) \ +{ \ + struct type *child, *parent, *old = elm; \ + int color; \ + if (PSCNV_RB_LEFT(elm, field) == NULL) \ + child = PSCNV_RB_RIGHT(elm, field); \ + else if (PSCNV_RB_RIGHT(elm, field) == NULL) \ + child = PSCNV_RB_LEFT(elm, field); \ + else { \ + struct type *left; \ + elm = PSCNV_RB_RIGHT(elm, field); \ + while ((left = PSCNV_RB_LEFT(elm, field)) != NULL) \ + elm = left; \ + child = PSCNV_RB_RIGHT(elm, field); \ + parent = PSCNV_RB_PARENT(elm, field); \ + color = PSCNV_RB_COLOR(elm, field); \ + if (child) \ + PSCNV_RB_PARENT(child, field) = parent; \ + if (parent) { \ + if (PSCNV_RB_LEFT(parent, field) == elm) \ + PSCNV_RB_LEFT(parent, field) = child; \ + else \ + PSCNV_RB_RIGHT(parent, field) = child; \ + PSCNV_RB_AUGMENT(parent); \ + } else \ + PSCNV_RB_ROOT(head) = child; \ + if (PSCNV_RB_PARENT(elm, field) == old) \ + parent = elm; \ + (elm)->field = (old)->field; \ + if (PSCNV_RB_PARENT(old, field)) { \ + if (PSCNV_RB_LEFT(PSCNV_RB_PARENT(old, field), field) == old)\ + PSCNV_RB_LEFT(PSCNV_RB_PARENT(old, field), field) = elm;\ + else \ + PSCNV_RB_RIGHT(PSCNV_RB_PARENT(old, field), field) = elm;\ + PSCNV_RB_AUGMENT(PSCNV_RB_PARENT(old, field)); \ + } else \ + PSCNV_RB_ROOT(head) = elm; \ + PSCNV_RB_PARENT(PSCNV_RB_LEFT(old, field), field) = elm; \ + if (PSCNV_RB_RIGHT(old, field)) \ + PSCNV_RB_PARENT(PSCNV_RB_RIGHT(old, field), field) = elm; \ + if (parent) { \ + left = parent; \ + do { \ + PSCNV_RB_AUGMENT(left); \ + } while ((left = PSCNV_RB_PARENT(left, field)) != NULL); \ + } \ + goto color; \ + } \ + parent = PSCNV_RB_PARENT(elm, field); \ + color = PSCNV_RB_COLOR(elm, field); \ + if (child) \ + PSCNV_RB_PARENT(child, field) = parent; \ + if (parent) { \ + if (PSCNV_RB_LEFT(parent, field) == elm) \ + PSCNV_RB_LEFT(parent, field) = child; \ + else \ + PSCNV_RB_RIGHT(parent, field) = child; \ + PSCNV_RB_AUGMENT(parent); \ + } else \ + PSCNV_RB_ROOT(head) = child; \ +color: \ + if (color == PSCNV_RB_BLACK) \ + name##_PSCNV_RB_REMOVE_COLOR(head, parent, child); \ + return (old); \ +} \ + \ +/* Inserts a node into the RB tree */ \ +attr struct type * \ +name##_PSCNV_RB_INSERT(struct name *head, struct type *elm) \ +{ \ + struct type *tmp; \ + struct type *parent = NULL; \ + int comp = 0; \ + tmp = PSCNV_RB_ROOT(head); \ + while (tmp) { \ + parent = tmp; \ + comp = (cmp)(elm, parent); \ + if (comp < 0) \ + tmp = PSCNV_RB_LEFT(tmp, field); \ + else if (comp > 0) \ + tmp = PSCNV_RB_RIGHT(tmp, field); \ + else \ + return (tmp); \ + } \ + PSCNV_RB_SET(elm, parent, field); \ + if (parent != NULL) { \ + if (comp < 0) \ + PSCNV_RB_LEFT(parent, field) = elm; \ + else \ + PSCNV_RB_RIGHT(parent, field) = elm; \ + PSCNV_RB_AUGMENT(parent); \ + } else \ + PSCNV_RB_ROOT(head) = elm; \ + name##_PSCNV_RB_INSERT_COLOR(head, elm); \ + return (NULL); \ +} \ + \ +/* Finds the node with the same key as elm */ \ +attr struct type * \ +name##_PSCNV_RB_FIND(struct name *head, struct type *elm) \ +{ \ + struct type *tmp = PSCNV_RB_ROOT(head); \ + int comp; \ + while (tmp) { \ + comp = cmp(elm, tmp); \ + if (comp < 0) \ + tmp = PSCNV_RB_LEFT(tmp, field); \ + else if (comp > 0) \ + tmp = PSCNV_RB_RIGHT(tmp, field); \ + else \ + return (tmp); \ + } \ + return (NULL); \ +} \ + \ +/* Finds the first node greater than or equal to the search key */ \ +attr struct type * \ +name##_PSCNV_RB_NFIND(struct name *head, struct type *elm) \ +{ \ + struct type *tmp = PSCNV_RB_ROOT(head); \ + struct type *res = NULL; \ + int comp; \ + while (tmp) { \ + comp = cmp(elm, tmp); \ + if (comp < 0) { \ + res = tmp; \ + tmp = PSCNV_RB_LEFT(tmp, field); \ + } \ + else if (comp > 0) \ + tmp = PSCNV_RB_RIGHT(tmp, field); \ + else \ + return (tmp); \ + } \ + return (res); \ +} \ + \ +/* ARGSUSED */ \ +attr struct type * \ +name##_PSCNV_RB_NEXT(struct type *elm) \ +{ \ + if (PSCNV_RB_RIGHT(elm, field)) { \ + elm = PSCNV_RB_RIGHT(elm, field); \ + while (PSCNV_RB_LEFT(elm, field)) \ + elm = PSCNV_RB_LEFT(elm, field); \ + } else { \ + if (PSCNV_RB_PARENT(elm, field) && \ + (elm == PSCNV_RB_LEFT(PSCNV_RB_PARENT(elm, field), field))) \ + elm = PSCNV_RB_PARENT(elm, field); \ + else { \ + while (PSCNV_RB_PARENT(elm, field) && \ + (elm == PSCNV_RB_RIGHT(PSCNV_RB_PARENT(elm, field), field)))\ + elm = PSCNV_RB_PARENT(elm, field); \ + elm = PSCNV_RB_PARENT(elm, field); \ + } \ + } \ + return (elm); \ +} \ + \ +/* ARGSUSED */ \ +attr struct type * \ +name##_PSCNV_RB_PREV(struct type *elm) \ +{ \ + if (PSCNV_RB_LEFT(elm, field)) { \ + elm = PSCNV_RB_LEFT(elm, field); \ + while (PSCNV_RB_RIGHT(elm, field)) \ + elm = PSCNV_RB_RIGHT(elm, field); \ + } else { \ + if (PSCNV_RB_PARENT(elm, field) && \ + (elm == PSCNV_RB_RIGHT(PSCNV_RB_PARENT(elm, field), field))) \ + elm = PSCNV_RB_PARENT(elm, field); \ + else { \ + while (PSCNV_RB_PARENT(elm, field) && \ + (elm == PSCNV_RB_LEFT(PSCNV_RB_PARENT(elm, field), field)))\ + elm = PSCNV_RB_PARENT(elm, field); \ + elm = PSCNV_RB_PARENT(elm, field); \ + } \ + } \ + return (elm); \ +} \ + \ +attr struct type * \ +name##_PSCNV_RB_MINMAX(struct name *head, int val) \ +{ \ + struct type *tmp = PSCNV_RB_ROOT(head); \ + struct type *parent = NULL; \ + while (tmp) { \ + parent = tmp; \ + if (val < 0) \ + tmp = PSCNV_RB_LEFT(tmp, field); \ + else \ + tmp = PSCNV_RB_RIGHT(tmp, field); \ + } \ + return (parent); \ +} + +#define PSCNV_RB_NEGINF -1 +#define PSCNV_RB_INF 1 + +#define PSCNV_RB_INSERT(name, x, y) name##_PSCNV_RB_INSERT(x, y) +#define PSCNV_RB_REMOVE(name, x, y) name##_PSCNV_RB_REMOVE(x, y) +#define PSCNV_RB_FIND(name, x, y) name##_PSCNV_RB_FIND(x, y) +#define PSCNV_RB_NFIND(name, x, y) name##_PSCNV_RB_NFIND(x, y) +#define PSCNV_RB_NEXT(name, x, y) name##_PSCNV_RB_NEXT(y) +#define PSCNV_RB_PREV(name, x, y) name##_PSCNV_RB_PREV(y) +#define PSCNV_RB_MIN(name, x) name##_PSCNV_RB_MINMAX(x, PSCNV_RB_NEGINF) +#define PSCNV_RB_MAX(name, x) name##_PSCNV_RB_MINMAX(x, PSCNV_RB_INF) + +#define PSCNV_RB_FOREACH(x, name, head) \ + for ((x) = PSCNV_RB_MIN(name, head); \ + (x) != NULL; \ + (x) = name##_PSCNV_RB_NEXT(x)) + +#define PSCNV_RB_FOREACH_REVERSE(x, name, head) \ + for ((x) = PSCNV_RB_MAX(name, head); \ + (x) != NULL; \ + (x) = name##_PSCNV_RB_PREV(x)) + +#endif /* __PSCNV_TREE_H__ */ diff --git a/driver/pscnv/pscnv_vm.c b/driver/pscnv/pscnv_vm.c new file mode 100644 index 00000000..27c0421a --- /dev/null +++ b/driver/pscnv/pscnv_vm.c @@ -0,0 +1,257 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#include "drmP.h" +#include "drm.h" +#include "nouveau_drv.h" +#include "pscnv_mem.h" +#include "pscnv_vm.h" +#include "pscnv_chan.h" + + +static int pscnv_vspace_bind (struct pscnv_vspace *vs, int fake) { + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + unsigned long flags; + int i; + BUG_ON(vs->vid); + spin_lock_irqsave(&dev_priv->vm->vs_lock, flags); + if (fake) { + vs->vid = -fake; + BUG_ON(dev_priv->vm->fake_vspaces[fake]); + dev_priv->vm->fake_vspaces[fake] = vs; + spin_unlock_irqrestore(&dev_priv->vm->vs_lock, flags); + return 0; + } else { + for (i = 1; i < 128; i++) + if (!dev_priv->vm->vspaces[i]) { + vs->vid = i; + dev_priv->vm->vspaces[i] = vs; + spin_unlock_irqrestore(&dev_priv->vm->vs_lock, flags); + return 0; + } + spin_unlock_irqrestore(&dev_priv->vm->vs_lock, flags); + NV_ERROR(vs->dev, "VM: Out of vspaces\n"); + return -ENOSPC; + } +} + +static void pscnv_vspace_unbind (struct pscnv_vspace *vs) { + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + unsigned long flags; + spin_lock_irqsave(&dev_priv->vm->vs_lock, flags); + if (vs->vid < 0) { + BUG_ON(dev_priv->vm->fake_vspaces[-vs->vid] != vs); + dev_priv->vm->fake_vspaces[-vs->vid] = 0; + } else { + BUG_ON(dev_priv->vm->vspaces[vs->vid] != vs); + dev_priv->vm->vspaces[vs->vid] = 0; + } + vs->vid = 0; + spin_unlock_irqrestore(&dev_priv->vm->vs_lock, flags); +} + +struct pscnv_vspace * +pscnv_vspace_new (struct drm_device *dev, uint64_t size, uint32_t flags, int fake) { + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct pscnv_vspace *res = kzalloc(sizeof *res, GFP_KERNEL); + if (!res) { + NV_ERROR(dev, "VM: Couldn't alloc vspace\n"); + return 0; + } + res->dev = dev; + res->size = size; + res->flags = flags; + kref_init(&res->ref); + mutex_init(&res->lock); + if (pscnv_vspace_bind(res, fake)) { + kfree(res); + return 0; + } + if (pscnv_vm_debug >= 1) { + NV_INFO(dev, "VM: Allocating vspace %d\n", res->vid); + } + if (dev_priv->vm->do_vspace_new(res)) { + pscnv_vspace_unbind(res); + kfree(res); + return 0; + } + return res; +} + +static void +pscnv_vspace_free_unmap(struct pscnv_mm_node *node) { + struct pscnv_bo *bo = node->tag; + drm_gem_object_unreference_unlocked(bo->gem); + pscnv_mm_free(node); +} + +void pscnv_vspace_ref_free(struct kref *ref) { + struct pscnv_vspace *vs = container_of(ref, struct pscnv_vspace, ref); + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + if (pscnv_vm_debug >= 1) { + NV_INFO(vs->dev, "VM: Freeing vspace %d\n", vs->vid); + } + if (vs->vid < 0) + pscnv_mm_takedown(vs->mm, pscnv_mm_free); + else + pscnv_mm_takedown(vs->mm, pscnv_vspace_free_unmap); + dev_priv->vm->do_vspace_free(vs); + pscnv_vspace_unbind(vs); + kfree(vs); +} + +static int +pscnv_vspace_unmap_node_unlocked(struct pscnv_mm_node *node) { + struct pscnv_vspace *vs = node->tag2; + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + struct pscnv_bo *bo = node->tag; + if (pscnv_vm_debug >= 1) { + NV_INFO(vs->dev, "VM: vspace %d: Unmapping range %llx-%llx.\n", vs->vid, node->start, node->start + node->size); + } + dev_priv->vm->do_unmap(vs, node->start, node->size); + + if (vs->vid >= 0) { + drm_gem_object_unreference(bo->gem); + } + pscnv_mm_free(node); + return 0; +} + +int +pscnv_vspace_map(struct pscnv_vspace *vs, struct pscnv_bo *bo, + uint64_t start, uint64_t end, int back, + struct pscnv_mm_node **res) +{ + struct pscnv_mm_node *node; + int ret; + struct drm_nouveau_private *dev_priv = vs->dev->dev_private; + mutex_lock(&vs->lock); + ret = dev_priv->vm->place_map(vs, bo, start, end, back, &node); + if (ret) { + mutex_unlock(&vs->lock); + return ret; + } + node->tag = bo; + node->tag2 = vs; + if (pscnv_vm_debug >= 1) + NV_INFO(vs->dev, "VM: vspace %d: Mapping BO %x/%d at %llx-%llx.\n", vs->vid, bo->cookie, bo->serial, node->start, + node->start + node->size); + ret = dev_priv->vm->do_map(vs, bo, node->start); + if (ret) { + pscnv_vspace_unmap_node_unlocked(node); + } + *res = node; + mutex_unlock(&vs->lock); + return ret; +} + +int +pscnv_vspace_unmap_node(struct pscnv_mm_node *node) { + struct pscnv_vspace *vs = node->tag2; + int ret; + mutex_lock(&vs->lock); + ret = pscnv_vspace_unmap_node_unlocked(node); + mutex_unlock(&vs->lock); + return ret; +} + +int +pscnv_vspace_unmap(struct pscnv_vspace *vs, uint64_t start) { + int ret; + mutex_lock(&vs->lock); + ret = pscnv_vspace_unmap_node_unlocked(pscnv_mm_find_node(vs->mm, start)); + mutex_unlock(&vs->lock); + return ret; +} + +static struct vm_operations_struct pscnv_vram_ops = { + .open = drm_gem_vm_open, + .close = drm_gem_vm_close, +}; + +static struct vm_operations_struct pscnv_sysram_ops = { + .open = drm_gem_vm_open, + .close = drm_gem_vm_close, + .fault = pscnv_sysram_vm_fault, +}; + +int pscnv_mmap(struct file *filp, struct vm_area_struct *vma) +{ + struct drm_file *priv = filp->private_data; + struct drm_device *dev = priv->minor->dev; + struct drm_nouveau_private *dev_priv = dev->dev_private; + struct drm_gem_object *obj; + struct pscnv_bo *bo; + int ret; + + if (vma->vm_pgoff * PAGE_SIZE < (1ull << 31)) + return drm_mmap(filp, vma); + + if (vma->vm_pgoff * PAGE_SIZE < (1ull << 32)) + return pscnv_chan_mmap(filp, vma); + + obj = drm_gem_object_lookup(dev, priv, (vma->vm_pgoff * PAGE_SIZE) >> 32); + if (!obj) + return -ENOENT; + bo = obj->driver_private; + + if (vma->vm_end - vma->vm_start > bo->size) { + drm_gem_object_unreference_unlocked(obj); + return -EINVAL; + } + switch (bo->flags & PSCNV_GEM_MEMTYPE_MASK) { + case PSCNV_GEM_VRAM_SMALL: + case PSCNV_GEM_VRAM_LARGE: + if ((ret = dev_priv->vm->map_user(bo))) { + drm_gem_object_unreference_unlocked(obj); + return ret; + } + + vma->vm_flags |= VM_RESERVED | VM_IO | VM_PFNMAP | VM_DONTEXPAND; + vma->vm_ops = &pscnv_vram_ops; + vma->vm_private_data = obj; + vma->vm_page_prot = pgprot_writecombine(vm_get_page_prot(vma->vm_flags)); + + vma->vm_file = filp; + + return remap_pfn_range(vma, vma->vm_start, + (dev_priv->fb_phys + bo->map1->start) >> PAGE_SHIFT, + vma->vm_end - vma->vm_start, PAGE_SHARED); + case PSCNV_GEM_SYSRAM_SNOOP: + case PSCNV_GEM_SYSRAM_NOSNOOP: + /* XXX */ + vma->vm_flags |= VM_RESERVED; + vma->vm_ops = &pscnv_sysram_ops; + vma->vm_private_data = obj; + + vma->vm_file = filp; + + return 0; + default: + drm_gem_object_unreference_unlocked(obj); + return -ENOSYS; + } +} diff --git a/driver/pscnv/pscnv_vm.h b/driver/pscnv/pscnv_vm.h new file mode 100644 index 00000000..4d2b647e --- /dev/null +++ b/driver/pscnv/pscnv_vm.h @@ -0,0 +1,84 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#ifndef __PSCNV_VM_H__ +#define __PSCNV_VM_H__ + +#include +#include "pscnv_mem.h" + +struct pscnv_bo; +struct pscnv_chan; + +struct pscnv_vspace { + int vid; + struct drm_device *dev; + struct mutex lock; + struct pscnv_mm *mm; + struct drm_file *filp; + struct kref ref; + uint64_t size; + uint32_t flags; + void *engdata; +}; + +struct pscnv_vm_engine { + void (*takedown) (struct drm_device *dev); + int (*do_vspace_new) (struct pscnv_vspace *vs); + void (*do_vspace_free) (struct pscnv_vspace *vs); + int (*place_map) (struct pscnv_vspace *, struct pscnv_bo *, uint64_t start, uint64_t end, int back, struct pscnv_mm_node **res); + int (*do_map) (struct pscnv_vspace *vs, struct pscnv_bo *bo, uint64_t offset); + int (*do_unmap) (struct pscnv_vspace *vs, uint64_t offset, uint64_t length); + int (*map_user) (struct pscnv_bo *); + int (*map_kernel) (struct pscnv_bo *); + void (*bar_flush) (struct drm_device *dev); + struct pscnv_vspace *fake_vspaces[4]; + struct pscnv_vspace *vspaces[128]; + spinlock_t vs_lock; +}; + +extern struct pscnv_vspace *pscnv_vspace_new(struct drm_device *, uint64_t size, uint32_t flags, int fake); +extern int pscnv_vspace_map(struct pscnv_vspace *, struct pscnv_bo *, uint64_t start, uint64_t end, int back, struct pscnv_mm_node **res); +extern int pscnv_vspace_unmap(struct pscnv_vspace *, uint64_t start); +extern int pscnv_vspace_unmap_node(struct pscnv_mm_node *node); + +extern void pscnv_vspace_ref_free(struct kref *ref); + +static inline void pscnv_vspace_ref(struct pscnv_vspace *vs) { + kref_get(&vs->ref); +} + +static inline void pscnv_vspace_unref(struct pscnv_vspace *vs) { + kref_put(&vs->ref, pscnv_vspace_ref_free); +} + +extern int pscnv_mmap(struct file *filp, struct vm_area_struct *vma); + + +int nv50_vm_init(struct drm_device *dev); +int nvc0_vm_init(struct drm_device *dev); + +#endif diff --git a/runtime/configure b/runtime/configure new file mode 100755 index 00000000..db698572 --- /dev/null +++ b/runtime/configure @@ -0,0 +1,38 @@ +#!/bin/sh + +topdir="../.." +gdev="gdev" +common="common" + +# configure options. +runtime="kernel" # use kernel-level runtime by default +driver="pscnv" # use pscnv by default. +debug=0 + +# parse the given options. +for option +do + case "$option" in + -*=*) optarg=`echo "$option" | sed 's/[-_a-zA-Z0-9]*=//'` ;; + *) optarg= ;; + esac + + case "$option" in + --runtime=*) + runtime="$optarg" ;; + --driver=*) + driver="$optarg" ;; + --debug) + debug=1 ;; + esac +done + +if [ $runtime = 'kernel' ]; then +cp -f ../$runtime/* . +cp -f $topdir/$common/*_def.h . +cp -f $topdir/$common/gdev_api.h . +else +cp -f ../$runtime/$gdev/* . +cp -f ../$runtime/$driver/* . +cp -f $topdir/$common/* . +fi diff --git a/runtime/kernel/Makefile b/runtime/kernel/Makefile new file mode 100644 index 00000000..e1fc72a1 --- /dev/null +++ b/runtime/kernel/Makefile @@ -0,0 +1,29 @@ +# Makefile + +CC = gcc +TARGET = libgdev +CFLAGS = -O3 -Wall +HEADERS = {gdev_api.h,gdev_lib.h,gdev_nvidia_def.h} + +OBJS = $(patsubst %.c,%.o,$(wildcard ./*.c)) +ZOMBIE = $(wildcard ./*~) + +all: $(OBJS) + $(CC) -shared -Wl,-soname,$(TARGET).so.1 -o ./$(TARGET).so.1.0.0 $(OBJS) + ldconfig -n ./ + +%.o:%.c + $(CC) -fPIC -c $^ -o $@ $(CFLAGS) + +install: + cp -f ./$(TARGET).so.1 /usr/lib64/$(TARGET).so.1 + ln -sf /usr/lib64/$(TARGET).so.1 /usr/lib64/$(TARGET).so + cp -f ./$(HEADERS) /usr/local/gdev/include + +uninstall: + rm -f /usr/lib64/$(TARGET).* + rm -f /usr/local/gdev/include/$(HEADERS) + +clean: + rm -f $(TARGET).so.* $(OBJS) $(ZOMBIE) + diff --git a/runtime/kernel/gdev_lib.c b/runtime/kernel/gdev_lib.c new file mode 100644 index 00000000..818969f3 --- /dev/null +++ b/runtime/kernel/gdev_lib.c @@ -0,0 +1,157 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +#include "gdev_api.h" +#include "gdev_ioctl_def.h" + +gdev_handle_t *gopen(int devnum) +{ + char devname[32]; + gdev_handle_t *handle = (gdev_handle_t*) malloc(sizeof(int)); + + sprintf(devname, "/dev/gdev%d", devnum); + *handle = open(devname, O_RDWR); + + return handle; +} + +int gclose(gdev_handle_t *handle) +{ + int fd = *handle; + return close(fd); +} + +uint64_t gmalloc(gdev_handle_t *handle, uint64_t size) +{ + gdev_ioctl_mem_t mem; + int fd = *handle; + + mem.size = size; + ioctl(fd, GDEV_IOCTL_GMALLOC, &mem); + + return mem.addr; +} + +void gfree(gdev_handle_t *handle, uint64_t addr) +{ + gdev_ioctl_mem_t mem; + int fd = *handle; + + mem.addr = addr; + ioctl(fd, GDEV_IOCTL_GFREE, &mem); +} + +int gmemcpy_from_device +(gdev_handle_t *handle, void *dst_buf, uint64_t src_addr, uint64_t size) +{ + gdev_ioctl_dma_t dma; + int fd = *handle; + + dma.src_addr = src_addr; + dma.dst_buf = dst_buf; + dma.size = size; + + return ioctl(fd, GDEV_IOCTL_GMEMCPY_FROM_DEVICE, &dma); +} + +int gmemcpy_to_device +(gdev_handle_t *handle, uint64_t dst_addr, void *src_buf, uint64_t size) +{ + gdev_ioctl_dma_t dma; + int fd = *handle; + + dma.dst_addr = dst_addr; + dma.src_buf = (void *)src_buf; + dma.size = size; + + return ioctl(fd, GDEV_IOCTL_GMEMCPY_TO_DEVICE, &dma); +} + +int gmemcpy_in_device +(gdev_handle_t *handle, uint64_t dst_addr, uint64_t src_addr, uint64_t size) +{ + gdev_ioctl_dma_t dma; + int fd = *handle; + + dma.dst_addr = dst_addr; + dma.src_addr = src_addr; + dma.size = size; + + return ioctl(fd, GDEV_IOCTL_GMEMCPY_IN_DEVICE, &dma); +} + +int glaunch(gdev_handle_t *handle, struct gdev_kernel *kernel, uint32_t *id) +{ + gdev_ioctl_launch_t launch; + int fd = *handle; + + launch.kernel = kernel; + launch.id = id; + + return ioctl(fd, GDEV_IOCTL_GLAUNCH, &launch); +} + +void gsync(gdev_handle_t *handle, uint32_t id) +{ + int fd = *handle; + ioctl(fd, GDEV_IOCTL_GSYNC, id); +} + +int gquery(gdev_handle_t *handle, uint32_t type, uint32_t *result) +{ + gdev_ioctl_query_t q; + int fd = *handle; + int ret; + + q.type = type; + if ((ret = ioctl(fd, GDEV_IOCTL_GQUERY, &q))) + return ret; + *result = q.result; + + return 0; +} + +int gtune(gdev_handle_t *handle, uint32_t type, uint32_t value) +{ + gdev_ioctl_tune_t c; + int fd = *handle; + int ret; + + c.type = type; + c.value = value; + if ((ret = ioctl(fd, GDEV_IOCTL_GTUNE, &c))) + return ret; + + return 0; +} + diff --git a/runtime/kernel/gdev_lib.h b/runtime/kernel/gdev_lib.h new file mode 100644 index 00000000..21c0b443 --- /dev/null +++ b/runtime/kernel/gdev_lib.h @@ -0,0 +1,30 @@ +/* +* Copyright 2011 Shinpei Kato +* All Rights Reserved. +* +* Permission is hereby granted, free of charge, to any person obtaining a +* copy of this software and associated documentation files (the "Software"), +* to deal in the Software without restriction, including without limitation +* the rights to use, copy, modify, merge, publish, distribute, sublicense, +* and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice (including the next +* paragraph) shall be included in all copies or substantial portions of the +* Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +* VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR +* OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, +* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +* OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef __GDEV_LIB_H__ +#define __GDEV_LIB_H__ + +typedef int gdev_handle_t; + +#endif diff --git a/runtime/user/gdev/Makefile b/runtime/user/gdev/Makefile new file mode 100644 index 00000000..e1fc72a1 --- /dev/null +++ b/runtime/user/gdev/Makefile @@ -0,0 +1,29 @@ +# Makefile + +CC = gcc +TARGET = libgdev +CFLAGS = -O3 -Wall +HEADERS = {gdev_api.h,gdev_lib.h,gdev_nvidia_def.h} + +OBJS = $(patsubst %.c,%.o,$(wildcard ./*.c)) +ZOMBIE = $(wildcard ./*~) + +all: $(OBJS) + $(CC) -shared -Wl,-soname,$(TARGET).so.1 -o ./$(TARGET).so.1.0.0 $(OBJS) + ldconfig -n ./ + +%.o:%.c + $(CC) -fPIC -c $^ -o $@ $(CFLAGS) + +install: + cp -f ./$(TARGET).so.1 /usr/lib64/$(TARGET).so.1 + ln -sf /usr/lib64/$(TARGET).so.1 /usr/lib64/$(TARGET).so + cp -f ./$(HEADERS) /usr/local/gdev/include + +uninstall: + rm -f /usr/lib64/$(TARGET).* + rm -f /usr/local/gdev/include/$(HEADERS) + +clean: + rm -f $(TARGET).so.* $(OBJS) $(ZOMBIE) + diff --git a/runtime/user/gdev/drm.h b/runtime/user/gdev/drm.h new file mode 100644 index 00000000..2ba71364 --- /dev/null +++ b/runtime/user/gdev/drm.h @@ -0,0 +1,789 @@ +/** + * \file drm.h + * Header for the Direct Rendering Manager + * + * \author Rickard E. (Rik) Faith + * + * \par Acknowledgments: + * Dec 1999, Richard Henderson , move to generic \c cmpxchg. + */ + +/* + * Copyright 1999 Precision Insight, Inc., Cedar Park, Texas. + * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California. + * All rights reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef _DRM_H_ +#define _DRM_H_ + +#if defined(__linux__) + +#include +#include +typedef unsigned int drm_handle_t; + +#else /* One of the BSDs */ + +#include +#include +typedef int8_t __s8; +typedef uint8_t __u8; +typedef int16_t __s16; +typedef uint16_t __u16; +typedef int32_t __s32; +typedef uint32_t __u32; +typedef int64_t __s64; +typedef uint64_t __u64; +typedef unsigned long drm_handle_t; + +#endif + +#define DRM_NAME "drm" /**< Name in kernel, /dev, and /proc */ +#define DRM_MIN_ORDER 5 /**< At least 2^5 bytes = 32 bytes */ +#define DRM_MAX_ORDER 22 /**< Up to 2^22 bytes = 4MB */ +#define DRM_RAM_PERCENT 10 /**< How much system ram can we lock? */ + +#define _DRM_LOCK_HELD 0x80000000U /**< Hardware lock is held */ +#define _DRM_LOCK_CONT 0x40000000U /**< Hardware lock is contended */ +#define _DRM_LOCK_IS_HELD(lock) ((lock) & _DRM_LOCK_HELD) +#define _DRM_LOCK_IS_CONT(lock) ((lock) & _DRM_LOCK_CONT) +#define _DRM_LOCKING_CONTEXT(lock) ((lock) & ~(_DRM_LOCK_HELD|_DRM_LOCK_CONT)) + +typedef unsigned int drm_context_t; +typedef unsigned int drm_drawable_t; +typedef unsigned int drm_magic_t; + +/** + * Cliprect. + * + * \warning: If you change this structure, make sure you change + * XF86DRIClipRectRec in the server as well + * + * \note KW: Actually it's illegal to change either for + * backwards-compatibility reasons. + */ +struct drm_clip_rect { + unsigned short x1; + unsigned short y1; + unsigned short x2; + unsigned short y2; +}; + +/** + * Drawable information. + */ +struct drm_drawable_info { + unsigned int num_rects; + struct drm_clip_rect *rects; +}; + +/** + * Texture region, + */ +struct drm_tex_region { + unsigned char next; + unsigned char prev; + unsigned char in_use; + unsigned char padding; + unsigned int age; +}; + +/** + * Hardware lock. + * + * The lock structure is a simple cache-line aligned integer. To avoid + * processor bus contention on a multiprocessor system, there should not be any + * other data stored in the same cache line. + */ +struct drm_hw_lock { + __volatile__ unsigned int lock; /**< lock variable */ + char padding[60]; /**< Pad to cache line */ +}; + +/** + * DRM_IOCTL_VERSION ioctl argument type. + * + * \sa drmGetVersion(). + */ +struct drm_version { + int version_major; /**< Major version */ + int version_minor; /**< Minor version */ + int version_patchlevel; /**< Patch level */ + size_t name_len; /**< Length of name buffer */ + char *name; /**< Name of driver */ + size_t date_len; /**< Length of date buffer */ + char *date; /**< User-space buffer to hold date */ + size_t desc_len; /**< Length of desc buffer */ + char *desc; /**< User-space buffer to hold desc */ +}; + +/** + * DRM_IOCTL_GET_UNIQUE ioctl argument type. + * + * \sa drmGetBusid() and drmSetBusId(). + */ +struct drm_unique { + size_t unique_len; /**< Length of unique */ + char *unique; /**< Unique name for driver instantiation */ +}; + +struct drm_list { + int count; /**< Length of user-space structures */ + struct drm_version *version; +}; + +struct drm_block { + int unused; +}; + +/** + * DRM_IOCTL_CONTROL ioctl argument type. + * + * \sa drmCtlInstHandler() and drmCtlUninstHandler(). + */ +struct drm_control { + enum { + DRM_ADD_COMMAND, + DRM_RM_COMMAND, + DRM_INST_HANDLER, + DRM_UNINST_HANDLER + } func; + int irq; +}; + +/** + * Type of memory to map. + */ +enum drm_map_type { + _DRM_FRAME_BUFFER = 0, /**< WC (no caching), no core dump */ + _DRM_REGISTERS = 1, /**< no caching, no core dump */ + _DRM_SHM = 2, /**< shared, cached */ + _DRM_AGP = 3, /**< AGP/GART */ + _DRM_SCATTER_GATHER = 4, /**< Scatter/gather memory for PCI DMA */ + _DRM_CONSISTENT = 5, /**< Consistent memory for PCI DMA */ + _DRM_GEM = 6, /**< GEM object */ +}; + +/** + * Memory mapping flags. + */ +enum drm_map_flags { + _DRM_RESTRICTED = 0x01, /**< Cannot be mapped to user-virtual */ + _DRM_READ_ONLY = 0x02, + _DRM_LOCKED = 0x04, /**< shared, cached, locked */ + _DRM_KERNEL = 0x08, /**< kernel requires access */ + _DRM_WRITE_COMBINING = 0x10, /**< use write-combining if available */ + _DRM_CONTAINS_LOCK = 0x20, /**< SHM page that contains lock */ + _DRM_REMOVABLE = 0x40, /**< Removable mapping */ + _DRM_DRIVER = 0x80 /**< Managed by driver */ +}; + +struct drm_ctx_priv_map { + unsigned int ctx_id; /**< Context requesting private mapping */ + void *handle; /**< Handle of map */ +}; + +/** + * DRM_IOCTL_GET_MAP, DRM_IOCTL_ADD_MAP and DRM_IOCTL_RM_MAP ioctls + * argument type. + * + * \sa drmAddMap(). + */ +struct drm_map { + unsigned long offset; /**< Requested physical address (0 for SAREA)*/ + unsigned long size; /**< Requested physical size (bytes) */ + enum drm_map_type type; /**< Type of memory to map */ + enum drm_map_flags flags; /**< Flags */ + void *handle; /**< User-space: "Handle" to pass to mmap() */ + /**< Kernel-space: kernel-virtual address */ + int mtrr; /**< MTRR slot used */ + /* Private data */ +}; + +/** + * DRM_IOCTL_GET_CLIENT ioctl argument type. + */ +struct drm_client { + int idx; /**< Which client desired? */ + int auth; /**< Is client authenticated? */ + unsigned long pid; /**< Process ID */ + unsigned long uid; /**< User ID */ + unsigned long magic; /**< Magic */ + unsigned long iocs; /**< Ioctl count */ +}; + +enum drm_stat_type { + _DRM_STAT_LOCK, + _DRM_STAT_OPENS, + _DRM_STAT_CLOSES, + _DRM_STAT_IOCTLS, + _DRM_STAT_LOCKS, + _DRM_STAT_UNLOCKS, + _DRM_STAT_VALUE, /**< Generic value */ + _DRM_STAT_BYTE, /**< Generic byte counter (1024bytes/K) */ + _DRM_STAT_COUNT, /**< Generic non-byte counter (1000/k) */ + + _DRM_STAT_IRQ, /**< IRQ */ + _DRM_STAT_PRIMARY, /**< Primary DMA bytes */ + _DRM_STAT_SECONDARY, /**< Secondary DMA bytes */ + _DRM_STAT_DMA, /**< DMA */ + _DRM_STAT_SPECIAL, /**< Special DMA (e.g., priority or polled) */ + _DRM_STAT_MISSED /**< Missed DMA opportunity */ + /* Add to the *END* of the list */ +}; + +/** + * DRM_IOCTL_GET_STATS ioctl argument type. + */ +struct drm_stats { + unsigned long count; + struct { + unsigned long value; + enum drm_stat_type type; + } data[15]; +}; + +/** + * Hardware locking flags. + */ +enum drm_lock_flags { + _DRM_LOCK_READY = 0x01, /**< Wait until hardware is ready for DMA */ + _DRM_LOCK_QUIESCENT = 0x02, /**< Wait until hardware quiescent */ + _DRM_LOCK_FLUSH = 0x04, /**< Flush this context's DMA queue first */ + _DRM_LOCK_FLUSH_ALL = 0x08, /**< Flush all DMA queues first */ + /* These *HALT* flags aren't supported yet + -- they will be used to support the + full-screen DGA-like mode. */ + _DRM_HALT_ALL_QUEUES = 0x10, /**< Halt all current and future queues */ + _DRM_HALT_CUR_QUEUES = 0x20 /**< Halt all current queues */ +}; + +/** + * DRM_IOCTL_LOCK, DRM_IOCTL_UNLOCK and DRM_IOCTL_FINISH ioctl argument type. + * + * \sa drmGetLock() and drmUnlock(). + */ +struct drm_lock { + int context; + enum drm_lock_flags flags; +}; + +/** + * DMA flags + * + * \warning + * These values \e must match xf86drm.h. + * + * \sa drm_dma. + */ +enum drm_dma_flags { + /* Flags for DMA buffer dispatch */ + _DRM_DMA_BLOCK = 0x01, /**< + * Block until buffer dispatched. + * + * \note The buffer may not yet have + * been processed by the hardware -- + * getting a hardware lock with the + * hardware quiescent will ensure + * that the buffer has been + * processed. + */ + _DRM_DMA_WHILE_LOCKED = 0x02, /**< Dispatch while lock held */ + _DRM_DMA_PRIORITY = 0x04, /**< High priority dispatch */ + + /* Flags for DMA buffer request */ + _DRM_DMA_WAIT = 0x10, /**< Wait for free buffers */ + _DRM_DMA_SMALLER_OK = 0x20, /**< Smaller-than-requested buffers OK */ + _DRM_DMA_LARGER_OK = 0x40 /**< Larger-than-requested buffers OK */ +}; + +/** + * DRM_IOCTL_ADD_BUFS and DRM_IOCTL_MARK_BUFS ioctl argument type. + * + * \sa drmAddBufs(). + */ +struct drm_buf_desc { + int count; /**< Number of buffers of this size */ + int size; /**< Size in bytes */ + int low_mark; /**< Low water mark */ + int high_mark; /**< High water mark */ + enum { + _DRM_PAGE_ALIGN = 0x01, /**< Align on page boundaries for DMA */ + _DRM_AGP_BUFFER = 0x02, /**< Buffer is in AGP space */ + _DRM_SG_BUFFER = 0x04, /**< Scatter/gather memory buffer */ + _DRM_FB_BUFFER = 0x08, /**< Buffer is in frame buffer */ + _DRM_PCI_BUFFER_RO = 0x10 /**< Map PCI DMA buffer read-only */ + } flags; + unsigned long agp_start; /**< + * Start address of where the AGP buffers are + * in the AGP aperture + */ +}; + +/** + * DRM_IOCTL_INFO_BUFS ioctl argument type. + */ +struct drm_buf_info { + int count; /**< Entries in list */ + struct drm_buf_desc *list; +}; + +/** + * DRM_IOCTL_FREE_BUFS ioctl argument type. + */ +struct drm_buf_free { + int count; + int *list; +}; + +/** + * Buffer information + * + * \sa drm_buf_map. + */ +struct drm_buf_pub { + int idx; /**< Index into the master buffer list */ + int total; /**< Buffer size */ + int used; /**< Amount of buffer in use (for DMA) */ + void *address; /**< Address of buffer */ +}; + +/** + * DRM_IOCTL_MAP_BUFS ioctl argument type. + */ +struct drm_buf_map { + int count; /**< Length of the buffer list */ +#ifdef __cplusplus + void *virt; +#else + void *virtual; /**< Mmap'd area in user-virtual */ +#endif + struct drm_buf_pub *list; /**< Buffer information */ +}; + +/** + * DRM_IOCTL_DMA ioctl argument type. + * + * Indices here refer to the offset into the buffer list in drm_buf_get. + * + * \sa drmDMA(). + */ +struct drm_dma { + int context; /**< Context handle */ + int send_count; /**< Number of buffers to send */ + int *send_indices; /**< List of handles to buffers */ + int *send_sizes; /**< Lengths of data to send */ + enum drm_dma_flags flags; /**< Flags */ + int request_count; /**< Number of buffers requested */ + int request_size; /**< Desired size for buffers */ + int *request_indices; /**< Buffer information */ + int *request_sizes; + int granted_count; /**< Number of buffers granted */ +}; + +enum drm_ctx_flags { + _DRM_CONTEXT_PRESERVED = 0x01, + _DRM_CONTEXT_2DONLY = 0x02 +}; + +/** + * DRM_IOCTL_ADD_CTX ioctl argument type. + * + * \sa drmCreateContext() and drmDestroyContext(). + */ +struct drm_ctx { + drm_context_t handle; + enum drm_ctx_flags flags; +}; + +/** + * DRM_IOCTL_RES_CTX ioctl argument type. + */ +struct drm_ctx_res { + int count; + struct drm_ctx *contexts; +}; + +/** + * DRM_IOCTL_ADD_DRAW and DRM_IOCTL_RM_DRAW ioctl argument type. + */ +struct drm_draw { + drm_drawable_t handle; +}; + +/** + * DRM_IOCTL_UPDATE_DRAW ioctl argument type. + */ +typedef enum { + DRM_DRAWABLE_CLIPRECTS, +} drm_drawable_info_type_t; + +struct drm_update_draw { + drm_drawable_t handle; + unsigned int type; + unsigned int num; + unsigned long long data; +}; + +/** + * DRM_IOCTL_GET_MAGIC and DRM_IOCTL_AUTH_MAGIC ioctl argument type. + */ +struct drm_auth { + drm_magic_t magic; +}; + +/** + * DRM_IOCTL_IRQ_BUSID ioctl argument type. + * + * \sa drmGetInterruptFromBusID(). + */ +struct drm_irq_busid { + int irq; /**< IRQ number */ + int busnum; /**< bus number */ + int devnum; /**< device number */ + int funcnum; /**< function number */ +}; + +enum drm_vblank_seq_type { + _DRM_VBLANK_ABSOLUTE = 0x0, /**< Wait for specific vblank sequence number */ + _DRM_VBLANK_RELATIVE = 0x1, /**< Wait for given number of vblanks */ + _DRM_VBLANK_EVENT = 0x4000000, /**< Send event instead of blocking */ + _DRM_VBLANK_FLIP = 0x8000000, /**< Scheduled buffer swap should flip */ + _DRM_VBLANK_NEXTONMISS = 0x10000000, /**< If missed, wait for next vblank */ + _DRM_VBLANK_SECONDARY = 0x20000000, /**< Secondary display controller */ + _DRM_VBLANK_SIGNAL = 0x40000000 /**< Send signal instead of blocking, unsupported */ +}; + +#define _DRM_VBLANK_TYPES_MASK (_DRM_VBLANK_ABSOLUTE | _DRM_VBLANK_RELATIVE) +#define _DRM_VBLANK_FLAGS_MASK (_DRM_VBLANK_EVENT | _DRM_VBLANK_SIGNAL | \ + _DRM_VBLANK_SECONDARY | _DRM_VBLANK_NEXTONMISS) + +struct drm_wait_vblank_request { + enum drm_vblank_seq_type type; + unsigned int sequence; + unsigned long signal; +}; + +struct drm_wait_vblank_reply { + enum drm_vblank_seq_type type; + unsigned int sequence; + long tval_sec; + long tval_usec; +}; + +/** + * DRM_IOCTL_WAIT_VBLANK ioctl argument type. + * + * \sa drmWaitVBlank(). + */ +union drm_wait_vblank { + struct drm_wait_vblank_request request; + struct drm_wait_vblank_reply reply; +}; + +#define _DRM_PRE_MODESET 1 +#define _DRM_POST_MODESET 2 + +/** + * DRM_IOCTL_MODESET_CTL ioctl argument type + * + * \sa drmModesetCtl(). + */ +struct drm_modeset_ctl { + __u32 crtc; + __u32 cmd; +}; + +/** + * DRM_IOCTL_AGP_ENABLE ioctl argument type. + * + * \sa drmAgpEnable(). + */ +struct drm_agp_mode { + unsigned long mode; /**< AGP mode */ +}; + +/** + * DRM_IOCTL_AGP_ALLOC and DRM_IOCTL_AGP_FREE ioctls argument type. + * + * \sa drmAgpAlloc() and drmAgpFree(). + */ +struct drm_agp_buffer { + unsigned long size; /**< In bytes -- will round to page boundary */ + unsigned long handle; /**< Used for binding / unbinding */ + unsigned long type; /**< Type of memory to allocate */ + unsigned long physical; /**< Physical used by i810 */ +}; + +/** + * DRM_IOCTL_AGP_BIND and DRM_IOCTL_AGP_UNBIND ioctls argument type. + * + * \sa drmAgpBind() and drmAgpUnbind(). + */ +struct drm_agp_binding { + unsigned long handle; /**< From drm_agp_buffer */ + unsigned long offset; /**< In bytes -- will round to page boundary */ +}; + +/** + * DRM_IOCTL_AGP_INFO ioctl argument type. + * + * \sa drmAgpVersionMajor(), drmAgpVersionMinor(), drmAgpGetMode(), + * drmAgpBase(), drmAgpSize(), drmAgpMemoryUsed(), drmAgpMemoryAvail(), + * drmAgpVendorId() and drmAgpDeviceId(). + */ +struct drm_agp_info { + int agp_version_major; + int agp_version_minor; + unsigned long mode; + unsigned long aperture_base; /* physical address */ + unsigned long aperture_size; /* bytes */ + unsigned long memory_allowed; /* bytes */ + unsigned long memory_used; + + /* PCI information */ + unsigned short id_vendor; + unsigned short id_device; +}; + +/** + * DRM_IOCTL_SG_ALLOC ioctl argument type. + */ +struct drm_scatter_gather { + unsigned long size; /**< In bytes -- will round to page boundary */ + unsigned long handle; /**< Used for mapping / unmapping */ +}; + +/** + * DRM_IOCTL_SET_VERSION ioctl argument type. + */ +struct drm_set_version { + int drm_di_major; + int drm_di_minor; + int drm_dd_major; + int drm_dd_minor; +}; + +/** DRM_IOCTL_GEM_CLOSE ioctl argument type */ +struct drm_gem_close { + /** Handle of the object to be closed. */ + __u32 handle; + __u32 pad; +}; + +/** DRM_IOCTL_GEM_FLINK ioctl argument type */ +struct drm_gem_flink { + /** Handle for the object being named */ + __u32 handle; + + /** Returned global name */ + __u32 name; +}; + +/** DRM_IOCTL_GEM_OPEN ioctl argument type */ +struct drm_gem_open { + /** Name of object being opened */ + __u32 name; + + /** Returned handle for the object */ + __u32 handle; + + /** Returned size of the object */ + __u64 size; +}; + +#include "drm_mode.h" + +#define DRM_IOCTL_BASE 'd' +#define DRM_IO(nr) _IO(DRM_IOCTL_BASE,nr) +#define DRM_IOR(nr,type) _IOR(DRM_IOCTL_BASE,nr,type) +#define DRM_IOW(nr,type) _IOW(DRM_IOCTL_BASE,nr,type) +#define DRM_IOWR(nr,type) _IOWR(DRM_IOCTL_BASE,nr,type) + +#define DRM_IOCTL_VERSION DRM_IOWR(0x00, struct drm_version) +#define DRM_IOCTL_GET_UNIQUE DRM_IOWR(0x01, struct drm_unique) +#define DRM_IOCTL_GET_MAGIC DRM_IOR( 0x02, struct drm_auth) +#define DRM_IOCTL_IRQ_BUSID DRM_IOWR(0x03, struct drm_irq_busid) +#define DRM_IOCTL_GET_MAP DRM_IOWR(0x04, struct drm_map) +#define DRM_IOCTL_GET_CLIENT DRM_IOWR(0x05, struct drm_client) +#define DRM_IOCTL_GET_STATS DRM_IOR( 0x06, struct drm_stats) +#define DRM_IOCTL_SET_VERSION DRM_IOWR(0x07, struct drm_set_version) +#define DRM_IOCTL_MODESET_CTL DRM_IOW(0x08, struct drm_modeset_ctl) +#define DRM_IOCTL_GEM_CLOSE DRM_IOW (0x09, struct drm_gem_close) +#define DRM_IOCTL_GEM_FLINK DRM_IOWR(0x0a, struct drm_gem_flink) +#define DRM_IOCTL_GEM_OPEN DRM_IOWR(0x0b, struct drm_gem_open) + +#define DRM_IOCTL_SET_UNIQUE DRM_IOW( 0x10, struct drm_unique) +#define DRM_IOCTL_AUTH_MAGIC DRM_IOW( 0x11, struct drm_auth) +#define DRM_IOCTL_BLOCK DRM_IOWR(0x12, struct drm_block) +#define DRM_IOCTL_UNBLOCK DRM_IOWR(0x13, struct drm_block) +#define DRM_IOCTL_CONTROL DRM_IOW( 0x14, struct drm_control) +#define DRM_IOCTL_ADD_MAP DRM_IOWR(0x15, struct drm_map) +#define DRM_IOCTL_ADD_BUFS DRM_IOWR(0x16, struct drm_buf_desc) +#define DRM_IOCTL_MARK_BUFS DRM_IOW( 0x17, struct drm_buf_desc) +#define DRM_IOCTL_INFO_BUFS DRM_IOWR(0x18, struct drm_buf_info) +#define DRM_IOCTL_MAP_BUFS DRM_IOWR(0x19, struct drm_buf_map) +#define DRM_IOCTL_FREE_BUFS DRM_IOW( 0x1a, struct drm_buf_free) + +#define DRM_IOCTL_RM_MAP DRM_IOW( 0x1b, struct drm_map) + +#define DRM_IOCTL_SET_SAREA_CTX DRM_IOW( 0x1c, struct drm_ctx_priv_map) +#define DRM_IOCTL_GET_SAREA_CTX DRM_IOWR(0x1d, struct drm_ctx_priv_map) + +#define DRM_IOCTL_SET_MASTER DRM_IO(0x1e) +#define DRM_IOCTL_DROP_MASTER DRM_IO(0x1f) + +#define DRM_IOCTL_ADD_CTX DRM_IOWR(0x20, struct drm_ctx) +#define DRM_IOCTL_RM_CTX DRM_IOWR(0x21, struct drm_ctx) +#define DRM_IOCTL_MOD_CTX DRM_IOW( 0x22, struct drm_ctx) +#define DRM_IOCTL_GET_CTX DRM_IOWR(0x23, struct drm_ctx) +#define DRM_IOCTL_SWITCH_CTX DRM_IOW( 0x24, struct drm_ctx) +#define DRM_IOCTL_NEW_CTX DRM_IOW( 0x25, struct drm_ctx) +#define DRM_IOCTL_RES_CTX DRM_IOWR(0x26, struct drm_ctx_res) +#define DRM_IOCTL_ADD_DRAW DRM_IOWR(0x27, struct drm_draw) +#define DRM_IOCTL_RM_DRAW DRM_IOWR(0x28, struct drm_draw) +#define DRM_IOCTL_DMA DRM_IOWR(0x29, struct drm_dma) +#define DRM_IOCTL_LOCK DRM_IOW( 0x2a, struct drm_lock) +#define DRM_IOCTL_UNLOCK DRM_IOW( 0x2b, struct drm_lock) +#define DRM_IOCTL_FINISH DRM_IOW( 0x2c, struct drm_lock) + +#define DRM_IOCTL_AGP_ACQUIRE DRM_IO( 0x30) +#define DRM_IOCTL_AGP_RELEASE DRM_IO( 0x31) +#define DRM_IOCTL_AGP_ENABLE DRM_IOW( 0x32, struct drm_agp_mode) +#define DRM_IOCTL_AGP_INFO DRM_IOR( 0x33, struct drm_agp_info) +#define DRM_IOCTL_AGP_ALLOC DRM_IOWR(0x34, struct drm_agp_buffer) +#define DRM_IOCTL_AGP_FREE DRM_IOW( 0x35, struct drm_agp_buffer) +#define DRM_IOCTL_AGP_BIND DRM_IOW( 0x36, struct drm_agp_binding) +#define DRM_IOCTL_AGP_UNBIND DRM_IOW( 0x37, struct drm_agp_binding) + +#define DRM_IOCTL_SG_ALLOC DRM_IOWR(0x38, struct drm_scatter_gather) +#define DRM_IOCTL_SG_FREE DRM_IOW( 0x39, struct drm_scatter_gather) + +#define DRM_IOCTL_WAIT_VBLANK DRM_IOWR(0x3a, union drm_wait_vblank) + +#define DRM_IOCTL_UPDATE_DRAW DRM_IOW(0x3f, struct drm_update_draw) + +#define DRM_IOCTL_MODE_GETRESOURCES DRM_IOWR(0xA0, struct drm_mode_card_res) +#define DRM_IOCTL_MODE_GETCRTC DRM_IOWR(0xA1, struct drm_mode_crtc) +#define DRM_IOCTL_MODE_SETCRTC DRM_IOWR(0xA2, struct drm_mode_crtc) +#define DRM_IOCTL_MODE_CURSOR DRM_IOWR(0xA3, struct drm_mode_cursor) +#define DRM_IOCTL_MODE_GETGAMMA DRM_IOWR(0xA4, struct drm_mode_crtc_lut) +#define DRM_IOCTL_MODE_SETGAMMA DRM_IOWR(0xA5, struct drm_mode_crtc_lut) +#define DRM_IOCTL_MODE_GETENCODER DRM_IOWR(0xA6, struct drm_mode_get_encoder) +#define DRM_IOCTL_MODE_GETCONNECTOR DRM_IOWR(0xA7, struct drm_mode_get_connector) +#define DRM_IOCTL_MODE_ATTACHMODE DRM_IOWR(0xA8, struct drm_mode_mode_cmd) +#define DRM_IOCTL_MODE_DETACHMODE DRM_IOWR(0xA9, struct drm_mode_mode_cmd) + +#define DRM_IOCTL_MODE_GETPROPERTY DRM_IOWR(0xAA, struct drm_mode_get_property) +#define DRM_IOCTL_MODE_SETPROPERTY DRM_IOWR(0xAB, struct drm_mode_connector_set_property) +#define DRM_IOCTL_MODE_GETPROPBLOB DRM_IOWR(0xAC, struct drm_mode_get_blob) +#define DRM_IOCTL_MODE_GETFB DRM_IOWR(0xAD, struct drm_mode_fb_cmd) +#define DRM_IOCTL_MODE_ADDFB DRM_IOWR(0xAE, struct drm_mode_fb_cmd) +#define DRM_IOCTL_MODE_RMFB DRM_IOWR(0xAF, unsigned int) +#define DRM_IOCTL_MODE_PAGE_FLIP DRM_IOWR(0xB0, struct drm_mode_crtc_page_flip) +#define DRM_IOCTL_MODE_DIRTYFB DRM_IOWR(0xB1, struct drm_mode_fb_dirty_cmd) + +/** + * Device specific ioctls should only be in their respective headers + * The device specific ioctl range is from 0x40 to 0x99. + * Generic IOCTLS restart at 0xA0. + * + * \sa drmCommandNone(), drmCommandRead(), drmCommandWrite(), and + * drmCommandReadWrite(). + */ +#define DRM_COMMAND_BASE 0x40 +#define DRM_COMMAND_END 0xA0 + +/** + * Header for events written back to userspace on the drm fd. The + * type defines the type of event, the length specifies the total + * length of the event (including the header), and user_data is + * typically a 64 bit value passed with the ioctl that triggered the + * event. A read on the drm fd will always only return complete + * events, that is, if for example the read buffer is 100 bytes, and + * there are two 64 byte events pending, only one will be returned. + * + * Event types 0 - 0x7fffffff are generic drm events, 0x80000000 and + * up are chipset specific. + */ +struct drm_event { + __u32 type; + __u32 length; +}; + +#define DRM_EVENT_VBLANK 0x01 +#define DRM_EVENT_FLIP_COMPLETE 0x02 + +struct drm_event_vblank { + struct drm_event base; + __u64 user_data; + __u32 tv_sec; + __u32 tv_usec; + __u32 sequence; + __u32 reserved; +}; + +/* typedef area */ +typedef struct drm_clip_rect drm_clip_rect_t; +typedef struct drm_drawable_info drm_drawable_info_t; +typedef struct drm_tex_region drm_tex_region_t; +typedef struct drm_hw_lock drm_hw_lock_t; +typedef struct drm_version drm_version_t; +typedef struct drm_unique drm_unique_t; +typedef struct drm_list drm_list_t; +typedef struct drm_block drm_block_t; +typedef struct drm_control drm_control_t; +typedef enum drm_map_type drm_map_type_t; +typedef enum drm_map_flags drm_map_flags_t; +typedef struct drm_ctx_priv_map drm_ctx_priv_map_t; +typedef struct drm_map drm_map_t; +typedef struct drm_client drm_client_t; +typedef enum drm_stat_type drm_stat_type_t; +typedef struct drm_stats drm_stats_t; +typedef enum drm_lock_flags drm_lock_flags_t; +typedef struct drm_lock drm_lock_t; +typedef enum drm_dma_flags drm_dma_flags_t; +typedef struct drm_buf_desc drm_buf_desc_t; +typedef struct drm_buf_info drm_buf_info_t; +typedef struct drm_buf_free drm_buf_free_t; +typedef struct drm_buf_pub drm_buf_pub_t; +typedef struct drm_buf_map drm_buf_map_t; +typedef struct drm_dma drm_dma_t; +typedef union drm_wait_vblank drm_wait_vblank_t; +typedef struct drm_agp_mode drm_agp_mode_t; +typedef enum drm_ctx_flags drm_ctx_flags_t; +typedef struct drm_ctx drm_ctx_t; +typedef struct drm_ctx_res drm_ctx_res_t; +typedef struct drm_draw drm_draw_t; +typedef struct drm_update_draw drm_update_draw_t; +typedef struct drm_auth drm_auth_t; +typedef struct drm_irq_busid drm_irq_busid_t; +typedef enum drm_vblank_seq_type drm_vblank_seq_type_t; + +typedef struct drm_agp_buffer drm_agp_buffer_t; +typedef struct drm_agp_binding drm_agp_binding_t; +typedef struct drm_agp_info drm_agp_info_t; +typedef struct drm_scatter_gather drm_scatter_gather_t; +typedef struct drm_set_version drm_set_version_t; + +#endif diff --git a/runtime/user/gdev/drm_mode.h b/runtime/user/gdev/drm_mode.h new file mode 100644 index 00000000..0fc7397c --- /dev/null +++ b/runtime/user/gdev/drm_mode.h @@ -0,0 +1,347 @@ +/* + * Copyright (c) 2007 Dave Airlie + * Copyright (c) 2007 Jakob Bornecrantz + * Copyright (c) 2008 Red Hat Inc. + * Copyright (c) 2007-2008 Tungsten Graphics, Inc., Cedar Park, TX., USA + * Copyright (c) 2007-2008 Intel Corporation + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#ifndef _DRM_MODE_H +#define _DRM_MODE_H + +#define DRM_DISPLAY_INFO_LEN 32 +#define DRM_CONNECTOR_NAME_LEN 32 +#define DRM_DISPLAY_MODE_LEN 32 +#define DRM_PROP_NAME_LEN 32 + +#define DRM_MODE_TYPE_BUILTIN (1<<0) +#define DRM_MODE_TYPE_CLOCK_C ((1<<1) | DRM_MODE_TYPE_BUILTIN) +#define DRM_MODE_TYPE_CRTC_C ((1<<2) | DRM_MODE_TYPE_BUILTIN) +#define DRM_MODE_TYPE_PREFERRED (1<<3) +#define DRM_MODE_TYPE_DEFAULT (1<<4) +#define DRM_MODE_TYPE_USERDEF (1<<5) +#define DRM_MODE_TYPE_DRIVER (1<<6) + +/* Video mode flags */ +/* bit compatible with the xorg definitions. */ +#define DRM_MODE_FLAG_PHSYNC (1<<0) +#define DRM_MODE_FLAG_NHSYNC (1<<1) +#define DRM_MODE_FLAG_PVSYNC (1<<2) +#define DRM_MODE_FLAG_NVSYNC (1<<3) +#define DRM_MODE_FLAG_INTERLACE (1<<4) +#define DRM_MODE_FLAG_DBLSCAN (1<<5) +#define DRM_MODE_FLAG_CSYNC (1<<6) +#define DRM_MODE_FLAG_PCSYNC (1<<7) +#define DRM_MODE_FLAG_NCSYNC (1<<8) +#define DRM_MODE_FLAG_HSKEW (1<<9) /* hskew provided */ +#define DRM_MODE_FLAG_BCAST (1<<10) +#define DRM_MODE_FLAG_PIXMUX (1<<11) +#define DRM_MODE_FLAG_DBLCLK (1<<12) +#define DRM_MODE_FLAG_CLKDIV2 (1<<13) + +/* DPMS flags */ +/* bit compatible with the xorg definitions. */ +#define DRM_MODE_DPMS_ON 0 +#define DRM_MODE_DPMS_STANDBY 1 +#define DRM_MODE_DPMS_SUSPEND 2 +#define DRM_MODE_DPMS_OFF 3 + +/* Scaling mode options */ +#define DRM_MODE_SCALE_NONE 0 /* Unmodified timing (display or + software can still scale) */ +#define DRM_MODE_SCALE_FULLSCREEN 1 /* Full screen, ignore aspect */ +#define DRM_MODE_SCALE_CENTER 2 /* Centered, no scaling */ +#define DRM_MODE_SCALE_ASPECT 3 /* Full screen, preserve aspect */ + +/* Dithering mode options */ +#define DRM_MODE_DITHERING_OFF 0 +#define DRM_MODE_DITHERING_ON 1 +#define DRM_MODE_DITHERING_AUTO 2 + +/* Dirty info options */ +#define DRM_MODE_DIRTY_OFF 0 +#define DRM_MODE_DIRTY_ON 1 +#define DRM_MODE_DIRTY_ANNOTATE 2 + +struct drm_mode_modeinfo { + __u32 clock; + __u16 hdisplay, hsync_start, hsync_end, htotal, hskew; + __u16 vdisplay, vsync_start, vsync_end, vtotal, vscan; + + __u32 vrefresh; + + __u32 flags; + __u32 type; + char name[DRM_DISPLAY_MODE_LEN]; +}; + +struct drm_mode_card_res { + __u64 fb_id_ptr; + __u64 crtc_id_ptr; + __u64 connector_id_ptr; + __u64 encoder_id_ptr; + __u32 count_fbs; + __u32 count_crtcs; + __u32 count_connectors; + __u32 count_encoders; + __u32 min_width, max_width; + __u32 min_height, max_height; +}; + +struct drm_mode_crtc { + __u64 set_connectors_ptr; + __u32 count_connectors; + + __u32 crtc_id; /**< Id */ + __u32 fb_id; /**< Id of framebuffer */ + + __u32 x, y; /**< Position on the frameuffer */ + + __u32 gamma_size; + __u32 mode_valid; + struct drm_mode_modeinfo mode; +}; + +#define DRM_MODE_ENCODER_NONE 0 +#define DRM_MODE_ENCODER_DAC 1 +#define DRM_MODE_ENCODER_TMDS 2 +#define DRM_MODE_ENCODER_LVDS 3 +#define DRM_MODE_ENCODER_TVDAC 4 + +struct drm_mode_get_encoder { + __u32 encoder_id; + __u32 encoder_type; + + __u32 crtc_id; /**< Id of crtc */ + + __u32 possible_crtcs; + __u32 possible_clones; +}; + +/* This is for connectors with multiple signal types. */ +/* Try to match DRM_MODE_CONNECTOR_X as closely as possible. */ +#define DRM_MODE_SUBCONNECTOR_Automatic 0 +#define DRM_MODE_SUBCONNECTOR_Unknown 0 +#define DRM_MODE_SUBCONNECTOR_DVID 3 +#define DRM_MODE_SUBCONNECTOR_DVIA 4 +#define DRM_MODE_SUBCONNECTOR_Composite 5 +#define DRM_MODE_SUBCONNECTOR_SVIDEO 6 +#define DRM_MODE_SUBCONNECTOR_Component 8 +#define DRM_MODE_SUBCONNECTOR_SCART 9 + +#define DRM_MODE_CONNECTOR_Unknown 0 +#define DRM_MODE_CONNECTOR_VGA 1 +#define DRM_MODE_CONNECTOR_DVII 2 +#define DRM_MODE_CONNECTOR_DVID 3 +#define DRM_MODE_CONNECTOR_DVIA 4 +#define DRM_MODE_CONNECTOR_Composite 5 +#define DRM_MODE_CONNECTOR_SVIDEO 6 +#define DRM_MODE_CONNECTOR_LVDS 7 +#define DRM_MODE_CONNECTOR_Component 8 +#define DRM_MODE_CONNECTOR_9PinDIN 9 +#define DRM_MODE_CONNECTOR_DisplayPort 10 +#define DRM_MODE_CONNECTOR_HDMIA 11 +#define DRM_MODE_CONNECTOR_HDMIB 12 +#define DRM_MODE_CONNECTOR_TV 13 +#define DRM_MODE_CONNECTOR_eDP 14 + +struct drm_mode_get_connector { + + __u64 encoders_ptr; + __u64 modes_ptr; + __u64 props_ptr; + __u64 prop_values_ptr; + + __u32 count_modes; + __u32 count_props; + __u32 count_encoders; + + __u32 encoder_id; /**< Current Encoder */ + __u32 connector_id; /**< Id */ + __u32 connector_type; + __u32 connector_type_id; + + __u32 connection; + __u32 mm_width, mm_height; /**< HxW in millimeters */ + __u32 subpixel; +}; + +#define DRM_MODE_PROP_PENDING (1<<0) +#define DRM_MODE_PROP_RANGE (1<<1) +#define DRM_MODE_PROP_IMMUTABLE (1<<2) +#define DRM_MODE_PROP_ENUM (1<<3) /* enumerated type with text strings */ +#define DRM_MODE_PROP_BLOB (1<<4) + +struct drm_mode_property_enum { + __u64 value; + char name[DRM_PROP_NAME_LEN]; +}; + +struct drm_mode_get_property { + __u64 values_ptr; /* values and blob lengths */ + __u64 enum_blob_ptr; /* enum and blob id ptrs */ + + __u32 prop_id; + __u32 flags; + char name[DRM_PROP_NAME_LEN]; + + __u32 count_values; + __u32 count_enum_blobs; +}; + +struct drm_mode_connector_set_property { + __u64 value; + __u32 prop_id; + __u32 connector_id; +}; + +struct drm_mode_get_blob { + __u32 blob_id; + __u32 length; + __u64 data; +}; + +struct drm_mode_fb_cmd { + __u32 fb_id; + __u32 width, height; + __u32 pitch; + __u32 bpp; + __u32 depth; + /* driver specific handle */ + __u32 handle; +}; + +#define DRM_MODE_FB_DIRTY_ANNOTATE_COPY 0x01 +#define DRM_MODE_FB_DIRTY_ANNOTATE_FILL 0x02 +#define DRM_MODE_FB_DIRTY_FLAGS 0x03 + +/* + * Mark a region of a framebuffer as dirty. + * + * Some hardware does not automatically update display contents + * as a hardware or software draw to a framebuffer. This ioctl + * allows userspace to tell the kernel and the hardware what + * regions of the framebuffer have changed. + * + * The kernel or hardware is free to update more then just the + * region specified by the clip rects. The kernel or hardware + * may also delay and/or coalesce several calls to dirty into a + * single update. + * + * Userspace may annotate the updates, the annotates are a + * promise made by the caller that the change is either a copy + * of pixels or a fill of a single color in the region specified. + * + * If the DRM_MODE_FB_DIRTY_ANNOTATE_COPY flag is given then + * the number of updated regions are half of num_clips given, + * where the clip rects are paired in src and dst. The width and + * height of each one of the pairs must match. + * + * If the DRM_MODE_FB_DIRTY_ANNOTATE_FILL flag is given the caller + * promises that the region specified of the clip rects is filled + * completely with a single color as given in the color argument. + */ + +struct drm_mode_fb_dirty_cmd { + __u32 fb_id; + __u32 flags; + __u32 color; + __u32 num_clips; + __u64 clips_ptr; +}; + +struct drm_mode_mode_cmd { + __u32 connector_id; + struct drm_mode_modeinfo mode; +}; + +#define DRM_MODE_CURSOR_BO (1<<0) +#define DRM_MODE_CURSOR_MOVE (1<<1) + +/* + * depending on the value in flags diffrent members are used. + * + * CURSOR_BO uses + * crtc + * width + * height + * handle - if 0 turns the cursor of + * + * CURSOR_MOVE uses + * crtc + * x + * y + */ +struct drm_mode_cursor { + __u32 flags; + __u32 crtc_id; + __s32 x; + __s32 y; + __u32 width; + __u32 height; + /* driver specific handle */ + __u32 handle; +}; + +struct drm_mode_crtc_lut { + __u32 crtc_id; + __u32 gamma_size; + + /* pointers to arrays */ + __u64 red; + __u64 green; + __u64 blue; +}; + +#define DRM_MODE_PAGE_FLIP_EVENT 0x01 +#define DRM_MODE_PAGE_FLIP_FLAGS DRM_MODE_PAGE_FLIP_EVENT + +/* + * Request a page flip on the specified crtc. + * + * This ioctl will ask KMS to schedule a page flip for the specified + * crtc. Once any pending rendering targeting the specified fb (as of + * ioctl time) has completed, the crtc will be reprogrammed to display + * that fb after the next vertical refresh. The ioctl returns + * immediately, but subsequent rendering to the current fb will block + * in the execbuffer ioctl until the page flip happens. If a page + * flip is already pending as the ioctl is called, EBUSY will be + * returned. + * + * The ioctl supports one flag, DRM_MODE_PAGE_FLIP_EVENT, which will + * request that drm sends back a vblank event (see drm.h: struct + * drm_event_vblank) when the page flip is done. The user_data field + * passed in with this ioctl will be returned as the user_data field + * in the vblank event struct. + * + * The reserved field must be zero until we figure out something + * clever to use it for. + */ + +struct drm_mode_crtc_page_flip { + __u32 crtc_id; + __u32 fb_id; + __u32 flags; + __u32 reserved; + __u64 user_data; +}; + +#endif diff --git a/runtime/user/gdev/gdev_lib.c b/runtime/user/gdev/gdev_lib.c new file mode 100644 index 00000000..72f15eb3 --- /dev/null +++ b/runtime/user/gdev/gdev_lib.c @@ -0,0 +1,94 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include +#include +#include "gdev_lib.h" +#include "drm.h" + +int drmIoctl(int fd, unsigned long request, void *arg) +{ + int ret; + + do { + ret = ioctl(fd, request, arg); + } while (ret == -1 && (errno == EINTR || errno == EAGAIN)); + return ret; +} + +/** + * Send a device-specific write command. + * + * \param fd file descriptor. + * \param drmCommandIndex command index + * \param data source pointer of the data to be written. + * \param size size of the data to be written. + * + * \return zero on success, or a negative value on failure. + * + * \internal + * It issues a write ioctl given by + * \code DRM_COMMAND_BASE + drmCommandIndex \endcode. + */ +int drmCommandWrite(int fd, unsigned long drmCommandIndex, void *data, + unsigned long size) +{ + unsigned long request; + + request = DRM_IOC( DRM_IOC_WRITE, DRM_IOCTL_BASE, + DRM_COMMAND_BASE + drmCommandIndex, size); + + if (drmIoctl(fd, request, data)) { + return -errno; + } + return 0; +} + + +/** + * Send a device-specific read-write command. + * + * \param fd file descriptor. + * \param drmCommandIndex command index + * \param data source pointer of the data to be read and written. + * \param size size of the data to be read and written. + * + * \return zero on success, or a negative value on failure. + * + * \internal + * It issues a read-write ioctl given by + * \code DRM_COMMAND_BASE + drmCommandIndex \endcode. + */ +int drmCommandWriteRead(int fd, unsigned long drmCommandIndex, void *data, + unsigned long size) +{ + unsigned long request; + + request = DRM_IOC( DRM_IOC_READ | DRM_IOC_WRITE, DRM_IOCTL_BASE, + DRM_COMMAND_BASE + drmCommandIndex, size); + + if (drmIoctl(fd, request, data)) + return -errno; + return 0; +} diff --git a/runtime/user/gdev/gdev_lib.h b/runtime/user/gdev/gdev_lib.h new file mode 100644 index 00000000..15efd4dd --- /dev/null +++ b/runtime/user/gdev/gdev_lib.h @@ -0,0 +1,113 @@ +/* +* Copyright 2011 Shinpei Kato +* All Rights Reserved. +* +* Permission is hereby granted, free of charge, to any person obtaining a +* copy of this software and associated documentation files (the "Software"), +* to deal in the Software without restriction, including without limitation +* the rights to use, copy, modify, merge, publish, distribute, sublicense, +* and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice (including the next +* paragraph) shall be included in all copies or substantial portions of the +* Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +* VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR +* OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, +* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +* OTHER DEALINGS IN THE SOFTWARE. +*/ + +#ifndef __GDEV_LIB_H__ +#define __GDEV_LIB_H__ + +#include /* ENOMEN, etc. */ +#include /* sched_yield, etc. */ +#include /* uint32_t, etc.*/ +#include /* printf, etc. */ +#include /* malloc/free, etc. */ +#include /* memcpy, etc. */ + +#define GDEV_DEV_GET(handle) (handle)->gdev +#define GDEV_DEV_SET(handle, dev) (handle)->gdev = (dev) +#define GDEV_VAS_GET(handle) (handle)->vas +#define GDEV_VAS_SET(handle, vas) (handle)->vas = (vas) +#define GDEV_CTX_GET(handle) (handle)->ctx +#define GDEV_CTX_SET(handle, ctx) (handle)->ctx = (ctx) +#define GDEV_DMA_GET(handle) (handle)->dma_mem +#define GDEV_DMA_SET(handle, mem) (handle)->dma_mem = (mem) +#define GDEV_PIPELINE_GET(handle) (handle)->pipeline_count +#define GDEV_PIPELINE_SET(handle, val) (handle)->pipeline_count = val +#define GDEV_CHUNK_GET(handle) (handle)->chunk_size +#define GDEV_CHUNK_SET(handle, val) (handle)->chunk_size = val +#define GDEV_MINOR_GET(handle) (handle)->dev_id +#define GDEV_MINOR_SET(handle, val) (handle)->dev_id = val +#define GDEV_PRINT(fmt, arg...) fprintf(stderr, "[gdev] " fmt, ##arg) +#define GDEV_DPRINT(fmt, arg...) \ + if (GDEV_DEBUG_PRINT) \ + fprintf(stderr, "[gdev:debug] " fmt, ##arg) + +#define MALLOC(x) malloc(x) +#define FREE(x) free(x) +#define SCHED_YIELD() sched_yield() +#define MB() //mb() +#define COPY_FROM_USER(dst, src, size) memcpy(dst, src, size) +#define COPY_TO_USER(dst, src, size) memcpy(dst, src, size) + +#define DRM_DIR_NAME "/dev/dri" +#define DRM_DEV_NAME "%s/card%d" +#define DRM_IOCTL_NR(n) _IOC_NR(n) +#define DRM_IOC_VOID _IOC_NONE +#define DRM_IOC_READ _IOC_READ +#define DRM_IOC_WRITE _IOC_WRITE +#define DRM_IOC_READWRITE _IOC_READ|_IOC_WRITE +#define DRM_IOC(dir, group, nr, size) _IOC(dir, group, nr, size) + +/** + * Gdev types: + */ +typedef struct gdev_vas gdev_vas_t; +typedef struct gdev_ctx gdev_ctx_t; +typedef struct gdev_mem gdev_mem_t; +typedef struct gdev_handle gdev_handle_t; +typedef struct gdev_device gdev_device_t; +typedef struct list_head gdev_list_t; + +/** + * Gdev handle struct: + */ +struct gdev_handle { + gdev_device_t *gdev; /* gdev handle object. */ + gdev_vas_t *vas; /* virtual address space object. */ + gdev_ctx_t *ctx; /* device context object. */ + gdev_mem_t **dma_mem; /* host-side DMA memory object (bounce buffer). */ + uint32_t chunk_size; /* configurable memcpy chunk size. */ + int pipeline_count; /* configurable memcpy pipeline count. */ + int dev_id; /* device ID. */ +}; + +/** + * Gdev device struct: + */ +struct gdev_device { + int id; + int fd; + uint32_t chipset; + void *compute; /* private set of compute functions */ +}; + +struct list_head { + struct list_head *next; + struct list_head *prev; + void *container; +}; + +extern int drmIoctl(int, unsigned long, void *); +extern int drmCommandWrite(int, unsigned long, void *, unsigned long); +extern int drmCommandWriteRead(int, unsigned long, void *, unsigned long); + +#endif diff --git a/runtime/user/pscnv/libpscnv.c b/runtime/user/pscnv/libpscnv.c new file mode 100644 index 00000000..564946ac --- /dev/null +++ b/runtime/user/pscnv/libpscnv.c @@ -0,0 +1,193 @@ +#include +#include +#include "drm.h" +#include "gdev_lib.h" +#include "libpscnv.h" +#include "pscnv_drm.h" + +int pscnv_getparam(int fd, uint64_t param, uint64_t *value) { + int ret; + struct drm_pscnv_getparam req; + req.param = param; + ret = drmCommandWriteRead(fd, DRM_PSCNV_GETPARAM, &req, sizeof(req)); + if (ret) + return ret; + if (value) + *value = req.value; + return 0; +} + +int pscnv_gem_new(int fd, uint32_t cookie, uint32_t flags, uint32_t tile_flags, uint64_t size, uint32_t *user, uint32_t *handle, uint64_t *map_handle) { + int ret; + struct drm_pscnv_gem_info req; + req.cookie = cookie; + req.flags = flags; + req.tile_flags = tile_flags; + req.size = size; + if (user) + memcpy(req.user, user, sizeof(req.user)); + ret = drmCommandWriteRead(fd, DRM_PSCNV_GEM_NEW, &req, sizeof(req)); + if (ret) + return ret; + if (handle) + *handle = req.handle; + if (map_handle) + *map_handle = req.map_handle; + return 0; +} + +int pscnv_gem_info(int fd, uint32_t handle, uint32_t *cookie, uint32_t *flags, uint32_t *tile_flags, uint64_t *size, uint64_t *map_handle, uint32_t *user) { + int ret; + struct drm_pscnv_gem_info req; + req.handle = handle; + ret = drmCommandWriteRead(fd, DRM_PSCNV_GEM_INFO, &req, sizeof(req)); + if (ret) + return ret; + if (cookie) + *cookie = req.cookie; + if (flags) + *flags = req.flags; + if (tile_flags) + *tile_flags = req.tile_flags; + if (size) + *size = req.size; + if (map_handle) + *map_handle = req.map_handle; + if (user) + memcpy(user, req.user, sizeof(req.user)); + return 0; +} + +int pscnv_gem_close(int fd, uint32_t handle) { + struct drm_gem_close req; + req.handle = handle; + return drmIoctl(fd, DRM_IOCTL_GEM_CLOSE, &req); +} + +int pscnv_gem_flink(int fd, uint32_t handle, uint32_t *name) { + int ret; + struct drm_gem_flink req; + req.handle = handle; + ret = drmIoctl(fd, DRM_IOCTL_GEM_FLINK, &req); + if (ret) + return ret; + if (name) + *name = req.name; + return 0; +} + +int pscnv_gem_open(int fd, uint32_t name, uint32_t *handle, uint64_t *size) { + int ret; + struct drm_gem_open req; + req.name = name; + ret = drmIoctl(fd, DRM_IOCTL_GEM_OPEN, &req); + if (ret) + return ret; + if (handle) + *handle = req.handle; + if (size) + *size = req.size; + return 0; +} + +int pscnv_vspace_new(int fd, uint32_t *vid) { + int ret; + struct drm_pscnv_vspace_req req; + ret = drmCommandWriteRead(fd, DRM_PSCNV_VSPACE_NEW, &req, sizeof(req)); + if (ret) + return ret; + if (vid) + *vid = req.vid; + return 0; +} + +int pscnv_vspace_free(int fd, uint32_t vid) { + struct drm_pscnv_vspace_req req; + req.vid = vid; + return drmCommandWriteRead(fd, DRM_PSCNV_VSPACE_FREE, &req, sizeof(req)); +} + +int pscnv_vspace_map(int fd, uint32_t vid, uint32_t handle, uint64_t start, uint64_t end, uint32_t back, uint32_t flags, uint64_t *offset) { + int ret; + struct drm_pscnv_vspace_map req; + req.vid = vid; + req.handle = handle; + req.start = start; + req.end = end; + req.back = back; + req.flags = flags; + ret = drmCommandWriteRead(fd, DRM_PSCNV_VSPACE_MAP, &req, sizeof(req)); + if (ret) + return ret; + if (offset) + *offset = req.offset; + return 0; +} + +int pscnv_vspace_unmap(int fd, uint32_t vid, uint64_t offset) { + struct drm_pscnv_vspace_unmap req; + req.vid = vid; + req.offset = offset; + return drmCommandWriteRead(fd, DRM_PSCNV_VSPACE_UNMAP, &req, sizeof(req)); +} + +int pscnv_chan_new(int fd, uint32_t vid, uint32_t *cid, uint64_t *map_handle) { + int ret; + struct drm_pscnv_chan_new req; + req.vid = vid; + ret = drmCommandWriteRead(fd, DRM_PSCNV_CHAN_NEW, &req, sizeof(req)); + if (ret) + return ret; + if (cid) + *cid = req.cid; + if (map_handle) + *map_handle = req.map_handle; + return 0; +} + +int pscnv_chan_free(int fd, uint32_t cid) { + struct drm_pscnv_chan_free req; + req.cid = cid; + return drmCommandWriteRead(fd, DRM_PSCNV_CHAN_FREE, &req, sizeof(req)); +} + +int pscnv_obj_vdma_new(int fd, uint32_t cid, uint32_t handle, uint32_t oclass, uint32_t flags, uint64_t start, uint64_t size) { + struct drm_pscnv_obj_vdma_new req; + req.cid = cid; + req.handle = handle; + req.oclass = oclass; + req.flags = flags; + req.start = start; + req.size = size; + return drmCommandWriteRead(fd, DRM_PSCNV_OBJ_VDMA_NEW, &req, sizeof(req)); +} + +int pscnv_fifo_init(int fd, uint32_t cid, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t pb_start) { + struct drm_pscnv_fifo_init req; + req.cid = cid; + req.pb_handle = pb_handle; + req.flags = flags; + req.slimask = slimask; + req.pb_start = pb_start; + return drmCommandWriteRead(fd, DRM_PSCNV_FIFO_INIT, &req, sizeof(req)); +} + +int pscnv_fifo_init_ib(int fd, uint32_t cid, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t ib_start, uint32_t ib_order) { + struct drm_pscnv_fifo_init_ib req; + req.cid = cid; + req.pb_handle = pb_handle; + req.flags = flags; + req.slimask = slimask; + req.ib_start = ib_start; + req.ib_order = ib_order; + return drmCommandWriteRead(fd, DRM_PSCNV_FIFO_INIT_IB, &req, sizeof(req)); +} + +int pscnv_obj_eng_new(int fd, uint32_t cid, uint32_t handle, uint32_t oclass, uint32_t flags) { + struct drm_pscnv_obj_eng_new req; + req.cid = cid; + req.handle = handle; + req.oclass = oclass; + req.flags = flags; + return drmCommandWriteRead(fd, DRM_PSCNV_OBJ_ENG_NEW, &req, sizeof(req)); +} diff --git a/runtime/user/pscnv/libpscnv.h b/runtime/user/pscnv/libpscnv.h new file mode 100644 index 00000000..812f4d12 --- /dev/null +++ b/runtime/user/pscnv/libpscnv.h @@ -0,0 +1,41 @@ +#ifndef LIBPSCNV_H +#define LIBPSCNV_H +#include + +#define PSCNV_GETPARAM_PCI_VENDOR 3 +#define PSCNV_GETPARAM_PCI_DEVICE 4 +#define PSCNV_GETPARAM_BUS_TYPE 5 +#define PSCNV_GETPARAM_FB_SIZE 8 +#define PSCNV_GETPARAM_CHIPSET_ID 11 +#define PSCNV_GETPARAM_GRAPH_UNITS 13 +#define PSCNV_GETPARAM_PTIMER_TIME 14 +#define PSCNV_GETPARAM_MP_COUNT 100 + +#define PSCNV_GEM_CONTIG 0x00000001 /* needs to be contiguous in VRAM */ +#define PSCNV_GEM_MAPPABLE 0x00000002 /* intended to be mmapped by host */ +#define PSCNV_GEM_MEMTYPE_MASK 0x0000000c +#define PSCNV_GEM_VRAM_SMALL 0x00000000 /* VRAM with small pages */ +#define PSCNV_GEM_SYSRAM_SNOOP 0x00000004 +#define PSCNV_GEM_VRAM_LARGE 0x00000008 /* VRAM with large pages */ +#define PSCNV_GEM_SYSRAM_NOSNOOP 0x0000000c +#define PSCNV_GEM_GART PSCNV_GEM_SYSRAM_SNOOP /* compat */ + +int pscnv_getparam(int fd, uint64_t param, uint64_t *value); +int pscnv_gem_new(int fd, uint32_t cookie, uint32_t flags, uint32_t tile_flags, uint64_t size, uint32_t *user, uint32_t *handle, uint64_t *map_handle); +int pscnv_gem_info(int fd, uint32_t handle, uint32_t *cookie, uint32_t *flags, uint32_t *tile_flags, uint64_t *size, uint64_t *map_handle, uint32_t *user); +int pscnv_gem_close(int fd, uint32_t handle); +int pscnv_gem_flink(int fd, uint32_t handle, uint32_t *name); +int pscnv_gem_open(int fd, uint32_t name, uint32_t *handle, uint64_t *size); +int pscnv_vspace_new(int fd, uint32_t *vid); +int pscnv_vspace_free(int fd, uint32_t vid); +int pscnv_vspace_map(int fd, uint32_t vid, uint32_t handle, uint64_t start, uint64_t end, uint32_t back, uint32_t flags, uint64_t *offset); +int pscnv_vspace_unmap(int fd, uint32_t vid, uint64_t offset); +int pscnv_chan_new(int fd, uint32_t vid, uint32_t *cid, uint64_t *map_handle); +int pscnv_chan_free(int fd, uint32_t cid); +int pscnv_obj_vdma_new(int fd, uint32_t cid, uint32_t handle, uint32_t oclass, uint32_t flags, uint64_t start, uint64_t size); +int pscnv_fifo_init(int fd, uint32_t cid, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t pb_start); +int pscnv_fifo_init_ib(int fd, uint32_t cid, uint32_t pb_handle, uint32_t flags, uint32_t slimask, uint64_t ib_start, uint32_t ib_order); +int pscnv_obj_eng_new(int fd, uint32_t cid, uint32_t handle, uint32_t oclass, uint32_t flags); +#define pscnv_obj_gr_new pscnv_obj_eng_new + +#endif diff --git a/runtime/user/pscnv/libpscnv_ib.c b/runtime/user/pscnv/libpscnv_ib.c new file mode 100644 index 00000000..4c98a90c --- /dev/null +++ b/runtime/user/pscnv/libpscnv_ib.c @@ -0,0 +1,158 @@ +#include "libpscnv_ib.h" +#include "libpscnv.h" +#include +#include +#include +#include + +int pscnv_ib_chan_new(int fd, int vid, struct pscnv_ib_chan **res, uint32_t pb_dma, uint32_t pb_order, uint32_t ib_order, uint32_t chipset) { + int ret; + struct pscnv_ib_chan *rr; + uint64_t map_handle; + *res = malloc(sizeof **res); + if (!*res) + return 1; + rr = *res; + rr->fd = fd; + rr->vid = vid; + if (!vid) { + ret = pscnv_vspace_new(fd, (uint32_t*)&rr->vid); + if (ret) + goto out_vs; + } + ret = pscnv_chan_new(fd, (uint32_t)rr->vid, (uint32_t*)&rr->cid, &map_handle); + if (ret) + goto out_chan; + + rr->chmap = mmap(0, 0x1000, PROT_READ | PROT_WRITE, + MAP_SHARED, fd, map_handle); + + if ((void*)rr->chmap == MAP_FAILED) + goto out_chmap; + rr->pb_dma = pb_dma; + + if (chipset != 0xc0) { + ret = pscnv_obj_vdma_new(fd, rr->cid, pb_dma, 0x3d, 0, 0, 1ull << 40); + if (ret) + goto out_vdma; + } + + rr->ib_order = ib_order; + if (!ib_order) + rr->ib_order = 9; + ret = pscnv_ib_bo_alloc(fd, rr->vid, 0xf1f01b, PSCNV_GEM_SYSRAM_SNOOP | PSCNV_GEM_MAPPABLE, 0, 8 << rr->ib_order, 0, &rr->ib); + if (ret) + goto out_ib; + rr->ib_map = rr->ib->map; + rr->ib_mask = (1 << rr->ib_order) - 1; + rr->ib_put = rr->ib_get = 0; + rr->pb_order = pb_order; + if (!pb_order) + rr->pb_order = 20; + ret = pscnv_ib_bo_alloc(fd, rr->vid, 0xf1f0, PSCNV_GEM_SYSRAM_SNOOP | PSCNV_GEM_MAPPABLE, 0, 1 << rr->pb_order, 0, &rr->pb); + if (ret) + goto out_pb; + rr->pb_map = rr->pb->map; + rr->pb_base = rr->pb->vm_base; + rr->pb_mask = (1 << rr->pb_order) - 1; + rr->pb_size = (1 << rr->pb_order); + rr->pb_pos = 0; + rr->pb_put = 0; + rr->pb_get = 0; + ret = pscnv_fifo_init_ib(fd, rr->cid, rr->pb_dma, 0, 1, rr->ib->vm_base, rr->ib_order); + if (ret) + goto out_fifo; + return 0; + +out_fifo: + pscnv_ib_bo_free(rr->pb); +out_pb: + pscnv_ib_bo_free(rr->ib); +out_ib: +out_vdma: + munmap((void*)rr->chmap, 0x1000); +out_chmap: + pscnv_chan_free(fd, rr->cid); +out_chan: + if (!vid) + pscnv_vspace_free(fd, rr->vid); +out_vs: + free(rr); + return 1; +} + +int pscnv_ib_bo_alloc(int fd, int vid, uint32_t cookie, uint32_t flags, uint32_t tile_flags, uint64_t size, uint32_t *user, struct pscnv_ib_bo **res) { + int ret; + struct pscnv_ib_bo *rr; + uint64_t map_handle; + *res = malloc(sizeof **res); + if (!*res) + return 1; + rr = *res; + rr->fd = fd; + rr->vid = vid; + rr->size = size; + ret = pscnv_gem_new(fd, cookie, flags, tile_flags, size, user, &rr->handle, &map_handle); + if (ret) + goto out_new; + if (vid) { + ret = pscnv_vspace_map(fd, vid, rr->handle, 0x20000000, 1ull << 40, 0, 0, &rr->vm_base); + if (ret) + goto out_vmap; + } + if (flags & PSCNV_GEM_MAPPABLE) { + rr->map = mmap(0, size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, map_handle); + if ((void*)rr->map == MAP_FAILED) + goto out_map; + } else + rr->map = 0; + return 0; + +out_map: + if (vid) + pscnv_vspace_unmap(fd, vid, rr->vm_base); +out_vmap: + pscnv_gem_close(fd, rr->handle); +out_new: + free(rr); + return 1; +} + +int pscnv_ib_bo_free(struct pscnv_ib_bo *bo) { + if (bo->map) + munmap(bo->map, bo->size); + if (bo->vid) + pscnv_vspace_unmap(bo->fd, bo->vid, bo->vm_base); + pscnv_gem_close(bo->fd, bo->handle); + free(bo); + return 0; +} + +int pscnv_ib_update_get(struct pscnv_ib_chan *ch) { + uint32_t lo = ch->chmap[0x58/4]; + uint32_t hi = ch->chmap[0x5c/4]; + if (hi & 0x80000000) { + uint64_t mg = ((uint64_t)hi << 32 | lo) & 0xffffffffffull; + ch->pb_get = mg - ch->pb_base; + } else { + ch->pb_get = 0; + } + return 0; +} + +int pscnv_ib_push(struct pscnv_ib_chan *ch, uint64_t base, uint32_t len, int flags) { + uint64_t w = base | (uint64_t)len << 40 | (uint64_t)flags << 40; + while (((ch->ib_put + 1) & ch->ib_mask) == ch->ib_get) { + uint32_t old = ch->ib_get; + ch->ib_get = ch->chmap[0x88/4]; + if (old == ch->ib_get) + sched_yield(); + } + ch->ib_map[ch->ib_put * 2] = w; + ch->ib_map[ch->ib_put * 2 + 1] = w >> 32; + ch->ib_put++; + ch->ib_put &= ch->ib_mask; + ch->chmap[0x8c/4] = ch->ib_put; + + return 0; +} diff --git a/runtime/user/pscnv/libpscnv_ib.h b/runtime/user/pscnv/libpscnv_ib.h new file mode 100644 index 00000000..e63a420a --- /dev/null +++ b/runtime/user/pscnv/libpscnv_ib.h @@ -0,0 +1,94 @@ +#ifndef LIBPSCNV_IB_H +#define LIBPSCNV_IB_H +#include +#include + +struct pscnv_ib_bo { + int fd; + int vid; + uint32_t handle; + void *map; + uint32_t size; + uint64_t vm_base; +}; + +struct pscnv_ib_chan { + int fd; + int vid; + int cid; + volatile uint32_t *chmap; + + uint32_t pb_dma; + + struct pscnv_ib_bo *ib; + uint32_t *ib_map; + uint32_t ib_order; + uint32_t ib_mask; + uint32_t ib_put; + uint32_t ib_get; + + struct pscnv_ib_bo *pb; + uint32_t *pb_map; + uint32_t pb_order; + uint64_t pb_base; + uint32_t pb_mask; + uint32_t pb_size; + uint32_t pb_pos; + uint32_t pb_put; + uint32_t pb_get; + +}; + +int pscnv_ib_chan_new(int fd, int vid, struct pscnv_ib_chan **res, uint32_t pb_dma, uint32_t pb_order, uint32_t ib_order, uint32_t chipset); +int pscnv_ib_bo_alloc(int fd, int vid, uint32_t cookie, uint32_t flags, uint32_t tile_flags, uint64_t size, uint32_t *user, struct pscnv_ib_bo **res); +int pscnv_ib_bo_free(struct pscnv_ib_bo *bo); +int pscnv_ib_push(struct pscnv_ib_chan *ch, uint64_t base, uint32_t len, int flags); +int pscnv_ib_update_get(struct pscnv_ib_chan *ch); + +static inline void FIRE_RING(struct pscnv_ib_chan *ch) { + if (ch->pb_pos != ch->pb_put) { + if (ch->pb_pos > ch->pb_put) { + pscnv_ib_push(ch, ch->pb_base + ch->pb_put, ch->pb_pos - ch->pb_put, 0); + } else { + pscnv_ib_push(ch, ch->pb_base + ch->pb_put, ch->pb_size - ch->pb_put, 0); + if (ch->pb_pos) + pscnv_ib_push(ch, ch->pb_base, ch->pb_pos, 0); + } + ch->pb_put = ch->pb_pos; + } +} + +static inline void OUT_RING(struct pscnv_ib_chan *ch, uint32_t word) { + while (((ch->pb_pos + 4) & ch->pb_mask) == ch->pb_get) { + uint32_t old = ch->pb_get; + FIRE_RING(ch); + pscnv_ib_update_get(ch); + if (old == ch->pb_get) + sched_yield(); + } + ch->pb_map[ch->pb_pos/4] = word; + ch->pb_pos += 4; + ch->pb_pos &= ch->pb_mask; +} + +static inline void BEGIN_RING +(struct pscnv_ib_chan *ch, int subc, int mthd, int len) { + OUT_RING(ch, mthd | subc << 13 | len << 18); +} + +static inline void BEGIN_RING_CONST +(struct pscnv_ib_chan *ch, int subc, int mthd, int len) { + OUT_RING(ch, mthd | subc << 13 | len << 18 | (0x4 << 28)); +} + +static inline void BEGIN_RING_NVC0 +(struct pscnv_ib_chan *ch, int subc, int mthd, int len) { + OUT_RING(ch, (0x2 << 28) | (len << 16) | (subc << 13) | (mthd >> 2)); +} + +static inline void BEGIN_RING_NVC0_CONST +(struct pscnv_ib_chan *ch, int subc, int mthd, int len) { + OUT_RING(ch, (0x6 << 28) | (len << 16) | (subc << 13) | (mthd >> 2)); +} + +#endif diff --git a/runtime/user/pscnv/pscnv_drm.h b/runtime/user/pscnv/pscnv_drm.h new file mode 100644 index 00000000..536cfaee --- /dev/null +++ b/runtime/user/pscnv/pscnv_drm.h @@ -0,0 +1,157 @@ +/* + * CDDL HEADER START + * + * The contents of this file are subject to the terms of the + * Common Development and Distribution License (the "License"). + * You may not use this file except in compliance with the License. + * + * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE + * or http://www.opensolaris.org/os/licensing. + * See the License for the specific language governing permissions + * and limitations under the License. + * + * When distributing Covered Code, include this CDDL HEADER in each + * file and include the License file at usr/src/OPENSOLARIS.LICENSE. + * If applicable, add the following below this CDDL HEADER, with the + * fields enclosed by brackets "[]" replaced with your own identifying + * information: Portions Copyright [yyyy] [name of copyright owner] + * + * CDDL HEADER END + */ + +/* + * Copyright 2010 PathScale Inc. All rights reserved. + * Use is subject to license terms. + */ + +#ifndef __PSCNV_DRM_H__ +#define __PSCNV_DRM_H__ + +#define PSCNV_DRM_HEADER_PATCHLEVEL 1 + +#define PSCNV_GETPARAM_PCI_VENDOR 3 +#define PSCNV_GETPARAM_PCI_DEVICE 4 +#define PSCNV_GETPARAM_BUS_TYPE 5 +#define PSCNV_GETPARAM_FB_SIZE 8 +#define PSCNV_GETPARAM_CHIPSET_ID 11 +#define PSCNV_GETPARAM_GRAPH_UNITS 13 +#define PSCNV_GETPARAM_PTIMER_TIME 14 +struct drm_pscnv_getparam { + uint64_t param; /* < */ + uint64_t value; /* > */ +}; + +enum pscnv_bus_type { + NV_AGP = 0, + NV_PCI = 1, + NV_PCIE = 2, +}; + +/* used for gem_new and gem_info */ +struct drm_pscnv_gem_info { /* n i */ + /* GEM handle used for identification */ + uint32_t handle; /* > < */ + /* cookie: free-form 32-bit number displayed in debug info. */ + uint32_t cookie; /* < > */ + /* misc flags, see below. */ + uint32_t flags; /* < > */ + uint32_t tile_flags; /* < > */ + uint64_t size; /* < > */ + /* offset inside drm fd's vm space usable for mmapping */ + uint64_t map_handle; /* > > */ + /* unused by kernel, can be used by userspace to store some info, + * like buffer format and tile_mode for DRI2 */ + uint32_t user[8]; /* < > */ +}; +#define PSCNV_GEM_CONTIG 0x00000001 /* needs to be contiguous in VRAM */ +#define PSCNV_GEM_MAPPABLE 0x00000002 /* intended to be mmapped by host */ +#define PSCNV_GEM_MEMTYPE_MASK 0x0000000c +#define PSCNV_GEM_VRAM_SMALL 0x00000000 /* VRAM with small pages */ +#define PSCNV_GEM_SYSRAM_SNOOP 0x00000004 +#define PSCNV_GEM_VRAM_LARGE 0x00000008 /* VRAM with large pages */ +#define PSCNV_GEM_SYSRAM_NOSNOOP 0x0000000c +#define PSCNV_GEM_GART PSCNV_GEM_SYSRAM_SNOOP /* compat */ + +/* for vspace_new and vspace_free */ +struct drm_pscnv_vspace_req { /* n f */ + uint32_t vid; /* > < */ +}; + +struct drm_pscnv_vspace_map { + uint32_t vid; /* < */ + uint32_t handle; /* < */ + uint64_t start; /* < */ + uint64_t end; /* < */ + uint32_t back; /* < */ + /* none defined yet */ + uint32_t flags; /* < */ + uint64_t offset; /* > */ +}; + +struct drm_pscnv_vspace_unmap { + uint32_t vid; /* < */ + uint32_t _pad; + uint64_t offset; /* < */ +}; + +struct drm_pscnv_chan_new { + uint32_t vid; /* < */ + uint32_t cid; /* > */ + /* The map handle that can be used to access channel control regs */ + uint64_t map_handle; /* > */ +}; + +struct drm_pscnv_chan_free { + uint32_t cid; /* < */ +}; + +struct drm_pscnv_obj_vdma_new { + uint32_t cid; /* < */ + uint32_t handle; /* < */ + uint32_t oclass; /* < */ + uint32_t flags; /* < */ + uint64_t start; /* < */ + uint64_t size; /* < */ +}; + +struct drm_pscnv_fifo_init { + uint32_t cid; /* < */ + uint32_t pb_handle; /* < */ + uint32_t flags; /* < */ + uint32_t slimask; /* < */ + uint64_t pb_start; /* < */ +}; + +struct drm_pscnv_fifo_init_ib { + uint32_t cid; /* < */ + uint32_t pb_handle; /* < */ + uint32_t flags; /* < */ + uint32_t slimask; /* < */ + uint64_t ib_start; /* < */ + uint32_t ib_order; /* < */ + uint32_t _pad; +}; + +struct drm_pscnv_obj_eng_new { + uint32_t cid; /* < */ + uint32_t handle; /* < */ + uint32_t oclass; /* < */ + uint32_t flags; /* < */ +}; + +#define DRM_PSCNV_GETPARAM 0x00 /* get some information from the card */ +#define DRM_PSCNV_GEM_NEW 0x20 /* create a new BO */ +#define DRM_PSCNV_GEM_INFO 0x21 /* get info about a BO */ +/* also uses generic GEM close, flink, open ioctls */ +#define DRM_PSCNV_VSPACE_NEW 0x22 /* Create a new virtual address space */ +#define DRM_PSCNV_VSPACE_FREE 0x23 /* Free a virtual address space */ +#define DRM_PSCNV_VSPACE_MAP 0x24 /* Maps a BO to a vspace */ +#define DRM_PSCNV_VSPACE_UNMAP 0x25 /* Unmaps a BO from a vspace */ +#define DRM_PSCNV_CHAN_NEW 0x26 /* Create a new channel */ +#define DRM_PSCNV_CHAN_FREE 0x27 /* Free a channel */ +#define DRM_PSCNV_OBJ_VDMA_NEW 0x28 /* Create a new vspace DMA object on a channel */ +#define DRM_PSCNV_FIFO_INIT 0x29 /* Initialises PFIFO processing on a channel */ +#define DRM_PSCNV_OBJ_ENG_NEW 0x2a /* Create a new engine object on a channel */ +#define DRM_PSCNV_FIFO_INIT_IB 0x2b /* Initialises IB PFIFO processing on a channel */ + +#endif /* __PSCNV_DRM_H__ */ diff --git a/runtime/user/pscnv/pscnv_gdev.c b/runtime/user/pscnv/pscnv_gdev.c new file mode 100644 index 00000000..b7669298 --- /dev/null +++ b/runtime/user/pscnv/pscnv_gdev.c @@ -0,0 +1,296 @@ +/* + * Copyright 2011 Shinpei Kato + * All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * VA LINUX SYSTEMS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "gdev_conf.h" +#include "gdev_lib.h" +#include "libpscnv.h" +#include "libpscnv_ib.h" +#include +#include +#include + +gdev_device_t gdev; + +#define PSCNV_BO_FLAGS_HOST (PSCNV_GEM_SYSRAM_SNOOP | PSCNV_GEM_MAPPABLE) + +/* allocate a new memory object. */ +static inline gdev_mem_t *__gdev_mem_alloc +(gdev_vas_t *vas, uint64_t size, uint32_t flags) +{ + gdev_mem_t *mem; + struct pscnv_ib_chan *chan = vas->pvas; + struct pscnv_ib_bo *bo; + + if (!(mem = (gdev_mem_t*) malloc(sizeof(*mem)))) + goto fail_mem; + + if (pscnv_ib_bo_alloc(chan->fd, chan->vid, 1, flags, 0, size, 0, &bo)) + goto fail_bo; + + mem->vas = vas; + mem->bo = bo; + mem->addr = bo->vm_base; + if (flags & PSCNV_BO_FLAGS_HOST) + mem->map = bo->map; + else + mem->map = NULL; + + __gdev_list_init(&mem->list_entry, (void *)mem); + + return mem; + +fail_bo: + GDEV_PRINT("Failed to allocate buffer object.\n"); + free(mem); +fail_mem: + return NULL; +} + +/* free the specified memory object. */ +static inline void __gdev_mem_free(gdev_mem_t *mem) +{ + struct pscnv_ib_bo *bo = mem->bo; + + if (pscnv_ib_bo_free(bo)) + GDEV_PRINT("Failed to free buffer object.\n"); + free(mem); +} + +/* initialize the compute engine. */ +int gdev_compute_init(gdev_device_t *gdev) +{ + uint32_t chipset = gdev->chipset; + + switch (chipset & 0xF0) { + case 0xC0: + nvc0_compute_setup(gdev); + break; + case 0x50: + case 0x80: + case 0x90: + case 0xA0: + /* TODO: create the compute and m2mf subchannels! */ + GDEV_PRINT("NV%x not supported.\n", chipset); + return -EINVAL; + default: + GDEV_PRINT("NV%x not supported.\n", chipset); + return -EINVAL; + } + + return 0; +} + +/* query a piece of the device-specific information. */ +int gdev_info_query(struct gdev_device *gdev, uint32_t type, uint32_t *result) +{ + int fd = gdev->fd; + + switch (type) { + case GDEV_QUERY_NVIDIA_MP_COUNT: + if (pscnv_getparam(fd, PSCNV_GETPARAM_MP_COUNT, (uint64_t *)result)) + return -EINVAL; + break; + default: + return -EINVAL; + } + + return 0; +} + +/* open a new Gdev object associated with the specified device. */ +gdev_device_t *gdev_dev_open(int devnum) +{ + char buf[64]; + int fd; + uint64_t chipset; + + sprintf(buf, DRM_DEV_NAME, DRM_DIR_NAME, devnum); + if ((fd = open(buf, O_RDWR, 0)) < 0) + return NULL; + + if (pscnv_getparam(fd, PSCNV_GETPARAM_CHIPSET_ID, &chipset)) { + close(fd); + return NULL; + } + + gdev.chipset = (uint32_t)chipset; + gdev.id = devnum; + gdev.fd = fd; + + gdev_compute_init(&gdev); + + return &gdev; +} + +/* close the specified Gdev object. */ +void gdev_dev_close(gdev_device_t *gdev) +{ + close(gdev->fd); +} + +/* allocate a new virual address space object. + pscnv_ib_chan_new() will allocate a channel object, too. */ +gdev_vas_t *gdev_vas_new(gdev_device_t *gdev, uint64_t size) +{ + int fd = gdev->fd; + uint32_t chipset = gdev->chipset; + gdev_vas_t *vas; + struct pscnv_ib_chan *chan; + + if (!(vas = malloc(sizeof(*vas)))) + goto fail_vas; + + if (pscnv_ib_chan_new(fd, 0, &chan, 0, 0, 0, chipset)) + goto fail_chan; + + vas->gdev = gdev; + vas->pvas = (void *)chan; /* private object. */ + + __gdev_list_init(&vas->memlist, NULL); + + return vas; + +fail_chan: + free(vas); +fail_vas: + GDEV_PRINT("Failed to create virtual address space.\n"); + return NULL; +} + +/* free the specified virtual address space object. */ +void gdev_vas_free(gdev_vas_t *vas) +{ + gdev_device_t *gdev = vas->gdev; + struct pscnv_ib_chan *chan = (struct pscnv_ib_chan *)vas->pvas; + int fd = gdev->fd; + + pscnv_ib_bo_free(chan->pb); + pscnv_ib_bo_free(chan->ib); + munmap((void*)chan->chmap, 0x1000); + pscnv_chan_free(chan->fd, chan->cid); + pscnv_vspace_free(fd, chan->vid); + free(chan); + free(vas); +} + +/* create a new GPU context object. + there are not many to do here, as we have already allocated a channel + object in gdev_vas_new(), i.e., @vas holds it. */ +gdev_ctx_t *gdev_ctx_new(gdev_device_t *gdev, gdev_vas_t *vas) +{ + gdev_ctx_t *ctx; + struct gdev_compute *compute = gdev->compute; + struct pscnv_ib_bo *fence_bo; + struct pscnv_ib_chan *chan = (struct pscnv_ib_chan *)vas->pvas; + uint32_t chipset = gdev->chipset; + int i; + + if (!(ctx = malloc(sizeof(*ctx)))) + goto fail_ctx; + + /* FIFO indirect buffer setup. */ + ctx->fifo.ib_order = chan->ib_order; + ctx->fifo.ib_map = chan->ib->map; + ctx->fifo.ib_bo = chan->ib; + ctx->fifo.ib_base = chan->ib->vm_base; + ctx->fifo.ib_mask = (1 << ctx->fifo.ib_order) - 1; + ctx->fifo.ib_put = ctx->fifo.ib_get = 0; + + /* FIFO push buffer setup. */ + ctx->fifo.pb_order = chan->pb_order; + ctx->fifo.pb_map = chan->pb->map; + ctx->fifo.pb_bo = chan->pb; + ctx->fifo.pb_base = chan->pb->vm_base; + ctx->fifo.pb_mask = (1 << ctx->fifo.pb_order) - 1; + ctx->fifo.pb_size = (1 << ctx->fifo.pb_order); + ctx->fifo.pb_pos = ctx->fifo.pb_put = ctx->fifo.pb_get = 0; + + /* FIFO init: it has already been done in gdev_vas_new(). */ + + /* FIFO command queue registers. */ + switch (chipset & 0xF0) { + case 0xC0: + ctx->fifo.regs = chan->chmap; + break; + default: + goto fail_fifo_reg; + } + + /* fences init. */ + if (pscnv_ib_bo_alloc(chan->fd, chan->vid, 1, PSCNV_BO_FLAGS_HOST, 0, + 0x1000, 0, &fence_bo)) + goto fail_fence_alloc; + ctx->fence.bo = fence_bo; + ctx->fence.map = fence_bo->map; + ctx->fence.addr = fence_bo->vm_base; + for (i = 0; i < GDEV_FENCE_COUNT; i++) { + ctx->fence.sequence[i] = 0; + } + + ctx->vas = vas; + ctx->pctx = chan; + + /* initialize the channel. */ + compute->init(ctx); + + return ctx; + +fail_fence_alloc: +fail_fifo_reg: + free(ctx); +fail_ctx: + GDEV_PRINT("Failed to create channel.\n"); + return NULL; +} + +/* destroy the specified GPU context object. */ +void gdev_ctx_free(gdev_ctx_t *ctx) +{ + pscnv_ib_bo_free(ctx->fence.bo); + free(ctx); +} + +/* allocate a new device memory object. */ +gdev_mem_t *gdev_malloc_device(gdev_vas_t *vas, uint64_t size) +{ + return __gdev_mem_alloc(vas, size, PSCNV_GEM_VRAM_SMALL); +} + +/* free the specified device memory object. */ +void gdev_free_device(gdev_mem_t *mem) +{ + return __gdev_mem_free(mem); +} + +/* allocate a new DMA (host) memory object. */ +gdev_mem_t *gdev_malloc_dma(gdev_vas_t *vas, uint64_t size) +{ + return __gdev_mem_alloc(vas, size, PSCNV_BO_FLAGS_HOST); +} + +/* free the specified DMA (host) memory object. */ +void gdev_free_dma(gdev_mem_t *mem) +{ + return __gdev_mem_free(mem); +} diff --git a/tests/common/loadstore.c b/tests/common/loadstore.c new file mode 100644 index 00000000..ab91002d --- /dev/null +++ b/tests/common/loadstore.c @@ -0,0 +1,157 @@ +#include "gdev_api.h" + +/* + mov b32 $r6 0xdeadcafe + mov b32 $r8 $nphysid + mov b32 $r10 $physid + ld b64 $r0d c0[0] + ld b64 $r2d c0[8] + ld b64 $r4d c0[16] + st b32 wb g[$r0d] $r6 + st b32 wb g[$r2d] $r8 + st b32 wb g[$r4d] $r10 + exit +*/ +uint32_t kcode[] = { + 0xf8019de2, + 0x1b7ab72b, + 0x08021c04, + 0x2c000000, + 0x0c029c04, + 0x2c000000, + 0x03f01ca6, + 0x14000000, + 0x23f09ca6, + 0x14000000, + 0x43f11ca6, + 0x14000000, + 0x00019c85, + 0x94000000, + 0x00221c85, + 0x94000000, + 0x00429c85, + 0x94000000, + 0x00001de7, + 0x80000000 +}; + +static inline unsigned __round_up_pow2(unsigned x) +{ + if (x == 0) + return 0; + x--; + x |= x >> 1; + x |= x >> 2; + x |= x >> 4; + x |= x >> 8; + x |= x >> 16; + + return ++x; +} + +int gdev_test_loadstore(void) +{ + uint32_t mp_count; + uint32_t stack_depth, stack_size; + uint32_t param_buf[6 * 4]; + uint32_t code_size, data_size; + uint32_t id; + uint64_t data_addr; + uint64_t result[3]; + + gdev_handle_t *handle; + struct gdev_kernel k; + + if (!(handle = gopen(0))) { + return -1; + } + + code_size = sizeof(kcode); + if (code_size & 0xff) + code_size = (code_size + 0x100) & ~0xff; + k.code_pc = 0; + k.cmem_segment = 0; + k.cmem_size = 3 * 8; /* 3 parameters */ + if (k.cmem_size == 0 || k.cmem_size & 0xff) + k.cmem_size = (k.cmem_size + 0x100) & ~0xff; + k.lmem_size = 0x100; /* just random */ + if (k.lmem_size & 0xf) + k.lmem_size = (k.lmem_size + 0x10) & ~0xf; + k.lmem_size_neg = 0; /* just random */ + if (k.lmem_size_neg & 0xf) + k.lmem_size_neg = (k.lmem_size_neg + 0x10) & ~0xf; + k.lmem_base = 0x01000000; + k.smem_size = 0x100; /* just random */ + if (k.smem_size & 0x7f) + k.smem_size = (k.smem_size + 0x80) & (~0x7f); + k.smem_base = 0x0; + + /* stack depth must be >= 16? */ + stack_depth = 16; + /* stack level is round_up(stack_depth/48) */ + k.stack_level = stack_depth / 48; + if (stack_depth % 48 != 0 && stack_depth > 16) + k.stack_level++; + /* this is the stack size */ + stack_size = k.stack_level * 16; + + /* FIXME: per-thread warp size may differ from 32. */ + k.warp_size = 32 * (stack_size + k.lmem_size + k.lmem_size_neg); + + /* FIXME: the number of active warps may differ from 48. */ + gquery(handle, GDEV_QUERY_NVIDIA_MP_COUNT, &mp_count); + k.lmem_size_total = 48 * mp_count * k.warp_size; + k.lmem_size_total = __round_up_pow2(k.lmem_size_total); + if (k.lmem_size_total > 128 * 1024) + k.lmem_size_total = 128 * 1024; + + if (!(k.code_addr = gmalloc(handle, code_size))) + return -1; + if (!(k.cmem_addr = gmalloc(handle, k.cmem_size))) + return -1; + if (!(k.lmem_addr = gmalloc(handle, k.lmem_size_total))) + return -1; + data_size = 3 * 8; + if (!(data_addr = gmalloc(handle, data_size))) + return -1; + + k.param_count = 6; /* note param is integer size. */ + k.param_buf = param_buf; + k.param_buf[0] = data_addr; + k.param_buf[1] = data_addr >> 32; + k.param_buf[2] = data_addr + 8; + k.param_buf[3] = (data_addr + 8) >> 32; + k.param_buf[4] = data_addr + 16; + k.param_buf[5] = (data_addr + 16) >> 32; + k.param_start = 0; + + k.reg_count = 32; + k.bar_count = 0; + k.grid_id = 1; + + k.grid_x = 1; + k.grid_y = 1; + k.grid_z = 1; + k.block_x = 1; + k.block_y = 1; + k.block_z = 1; + + gmemcpy_to_device(handle, k.code_addr, kcode, code_size); + + glaunch(handle, &k, &id); + gsync(handle, id); + + gmemcpy_from_device(handle, result, data_addr, data_size); + + gfree(handle, data_addr); + gfree(handle, k.code_addr); + gfree(handle, k.cmem_addr); + gfree(handle, k.lmem_addr); + + gclose(handle); + + if ((result[0] & 0xffffffff) == 0xdeadcafe) + return 0; + else + return -1; +} diff --git a/tests/common/matrixadd.c b/tests/common/matrixadd.c new file mode 100644 index 00000000..87418564 --- /dev/null +++ b/tests/common/matrixadd.c @@ -0,0 +1,257 @@ +#include "gdev_api.h" + +/* +00000000: 00005de4 28004404 mov b32 $r1 c1[0x100] +00000008: 98009c04 2c000000 mov b32 $r2 $ctaidy +00000010: 88011c04 2c000000 mov b32 $r4 $tidy +00000018: 94001c04 2c000000 mov b32 $r0 $ctaidx +00000020: 8400dc04 2c000000 mov b32 $r3 $tidx +00000028: 30209c03 20084000 add $r2 (mul u32 $r2 u32 c0[0xc]) $r4 +00000030: 20001c03 20064000 add $r0 (mul u32 $r0 u32 c0[0x8]) $r3 +00000038: e021dc03 188e4000 set $p0 0x1 lt u32 $r2 c0[0x38] +00000040: e001dc03 18804000 set $p0 0x1 lt u32 $r0 c0[0x38] and $p0 +00000048: 000021e7 80000000 (not $p0) exit +00000050: e000dc03 20044000 add $r3 (mul u32 $r0 u32 c0[0x38]) $r2 +00000058: 10015de2 18000000 mov b32 $r5 0x4 +00000060: 10311ce3 5000c000 mul high $r4 s32 $r3 s32 0x4 +00000068: 80319ca3 200b8000 add $r6 $c (mul s32 $r3 s32 $r5) c0[0x20] +00000070: 9041dc43 48004000 add b32 $r7 $r4 c0[0x24] $c +00000078: a0321ca3 200b8000 add $r8 $c (mul s32 $r3 s32 $r5) c0[0x28] +00000080: 00609c85 84000000 ld b32 $r2 ca g[$r6d] +00000088: b0425c43 48004000 add b32 $r9 $r4 c0[0x2c] $c +00000090: c0329ca3 200b8000 add $r10 $c (mul s32 $r3 s32 $r5) c0[0x30] +00000098: 00801c85 84000000 ld b32 $r0 ca g[$r8d] +000000a0: d042dc43 48004000 add b32 $r11 $r4 c0[0x34] $c +000000a8: 00201c03 48000000 add b32 $r0 $r2 $r0 +000000b0: 00a01c85 94000000 st b32 wb g[$r10d] $r0 +000000b8: 00001de7 80000000 exit + */ +uint32_t kcode[] = { + 0x00005de4, + 0x28004404, + 0x98009c04, + 0x2c000000, + 0x88011c04, + 0x2c000000, + 0x94001c04, + 0x2c000000, + 0x8400dc04, + 0x2c000000, + 0x30209c03, + 0x20084000, + 0x20001c03, + 0x20064000, + 0xe021dc03, + 0x188e4000, + 0xe001dc03, + 0x18804000, + 0x000021e7, + 0x80000000, + 0xe000dc03, + 0x20044000, + 0x10015de2, + 0x18000000, + 0x10311ce3, + 0x5000c000, + 0x80319ca3, + 0x200b8000, + 0x9041dc43, + 0x48004000, + 0xa0321ca3, + 0x200b8000, + 0x00609c85, + 0x84000000, + 0xb0425c43, + 0x48004000, + 0xc0329ca3, + 0x200b8000, + 0x00801c85, + 0x84000000, + 0xd042dc43, + 0x48004000, + 0x00201c03, + 0x48000000, + 0x00a01c85, + 0x94000000, + 0x00001de7, + 0x80000000 +}; + +uint32_t c0[] = { + 0x0, + 0x0, + 0x0, + 0x0, + 0x0, + 0x0, + 0x0, + 0x0, + 0x0, + 0x0, + 0x0, + 0x0, + 0x0, + 0x0, + 0x0 +}; + +#define PARAM_SIZE 0x3c +#define STACK_DEPTH 0xc +#define LOCAL_SIZE 0x0 +#define SHARED_SIZE 0x0 +#define REG_COUNT 0xc +#define BARRIER_COUNT 0x0 +#define NVCC_PARAM_OFFSET 0x20 + +static inline unsigned __round_up_pow2(unsigned x) +{ + if (x == 0) + return 0; + x--; + x |= x >> 1; + x |= x >> 2; + x |= x >> 4; + x |= x >> 8; + x |= x >> 16; + + return ++x; +} + +int gdev_test_matrixadd(uint32_t *a, uint32_t *b, uint32_t *c, int n) +{ + int i, j, idx; + uint32_t mp_count; + uint32_t code_size, a_size, b_size, c_size; + uint32_t stack_depth, stack_size; + uint32_t param_buf[PARAM_SIZE]; + uint64_t a_addr, b_addr, c_addr; + uint64_t result[3]; + + gdev_handle_t *handle; + gdev_kernel_t k; + + /* initialize A[] & B[] */ + for (i = 0; i < n; i++) { + for(j = 0; j < n; j++) { + idx = i * n + j; + a[idx] = i; + b[idx] = j; + } + } + + if (!(handle = gopen(0))) { + return -1; + } + + code_size = sizeof(kcode); + if (code_size & 0xff) + code_size = (code_size + 0x100) & ~0xff; + a_size = n * n * sizeof(uint32_t); + b_size = n * n * sizeof(uint32_t); + c_size = n * n * sizeof(uint32_t); + + k.code_pc = 0; + k.cmem_segment = 0; + k.cmem_size = PARAM_SIZE; + if (k.cmem_size == 0 || k.cmem_size & 0xff) + k.cmem_size = (k.cmem_size + 0x100) & ~0xff; + k.lmem_size = LOCAL_SIZE; + if (k.lmem_size & 0xf) + k.lmem_size = (k.lmem_size + 0x10) & ~0xf; + k.lmem_size_neg = 0; /* just random */ + if (k.lmem_size_neg & 0xf) + k.lmem_size_neg = (k.lmem_size_neg + 0x10) & ~0xf; + k.lmem_base = 0x01000000; + k.smem_size = SHARED_SIZE; + if (k.smem_size & 0x7f) + k.smem_size = (k.smem_size + 0x80) & (~0x7f); + k.smem_base = 0x0; + + /* stack depth must be >= 16? */ + stack_depth = STACK_DEPTH > 16 ? STACK_DEPTH : 16; + /* stack level is round_up(stack_depth/48) */ + k.stack_level = stack_depth / 48; + if (stack_depth % 48 != 0) + k.stack_level++; + /* this is the stack size */ + stack_size = k.stack_level * 16; + + /* FIXME: per-thread warp size may differ from 32. */ + k.warp_size = 32 * (stack_size + k.lmem_size + k.lmem_size_neg); + + /* FIXME: the number of active warps may differ from 48. */ + gquery(handle, GDEV_QUERY_NVIDIA_MP_COUNT, &mp_count); + k.lmem_size_total = 48 * mp_count * k.warp_size; + k.lmem_size_total = __round_up_pow2(k.lmem_size_total); + if (k.lmem_size_total > 128 * 1024) + k.lmem_size_total = 128 * 1024; + + if (!(a_addr = gmalloc(handle, a_size))) + return -1; + if (!(b_addr = gmalloc(handle, b_size))) + return -1; + if (!(c_addr = gmalloc(handle, c_size))) + return -1; + if (!(k.code_addr = gmalloc(handle, code_size))) + return -1; + if (!(k.cmem_addr = gmalloc(handle, k.cmem_size))) + return -1; + if (!(k.lmem_addr = gmalloc(handle, k.lmem_size_total))) + return -1; + + k.param_count = PARAM_SIZE / 4; /* note param is integer size. */ + k.param_start = 0; + k.param_buf = c0; + k.param_buf[NVCC_PARAM_OFFSET/4 + 0] = a_addr; + k.param_buf[NVCC_PARAM_OFFSET/4 + 1] = a_addr >> 32; + k.param_buf[NVCC_PARAM_OFFSET/4 + 2] = b_addr; + k.param_buf[NVCC_PARAM_OFFSET/4 + 3] = b_addr >> 32; + k.param_buf[NVCC_PARAM_OFFSET/4 + 4] = c_addr; + k.param_buf[NVCC_PARAM_OFFSET/4 + 5] = c_addr >> 32; + k.param_buf[NVCC_PARAM_OFFSET/4 + 6] = n; + + k.reg_count = REG_COUNT; + k.bar_count = BARRIER_COUNT; + k.grid_id = 1; + + k.block_x = n < 32 ? n : 32; + k.block_y = n < 32 ? n : 32; + k.block_z = 1; + k.grid_x = n / k.block_x; + if(n % k.block_x != 0) + k.grid_x++; + k.grid_y = n / k.block_y; + k.grid_z = 1; + + gmemcpy_to_device(handle, k.code_addr, kcode, code_size); + gmemcpy_to_device(handle, a_addr, a, a_size); + gmemcpy_to_device(handle, b_addr, b, b_size); + + glaunch(handle, &k); + gsync(handle); + + gmemcpy_from_device(handle, c, c_addr, c_size); + + gfree(handle, a_addr); + gfree(handle, b_addr); + gfree(handle, c_addr); + gfree(handle, k.code_addr); + gfree(handle, k.cmem_addr); + gfree(handle, k.lmem_addr); + + gclose(handle); + + i = j = idx = 0; + while (i < n) { + while (j < n) { + idx = i * n + j; + if (c[idx] != a[idx] + b[idx]) { + return -1; + } + j++; + } + i++; + } + + return 0; +} diff --git a/tests/common/matrixadd.cu b/tests/common/matrixadd.cu new file mode 100644 index 00000000..c1486a9c --- /dev/null +++ b/tests/common/matrixadd.cu @@ -0,0 +1,10 @@ +#include +#include +extern "C" __global__ void bench(uint32_t *a, uint32_t *b, uint32_t *c, uint32_t n){ + int i = blockIdx.x * blockDim.x + threadIdx.x; + int j = blockIdx.y * blockDim.y + threadIdx.y; + if(igkEfTO2 zixd`D1k#I*g@tl|f`7mkqC(pI2l{<8-`tPAZFFGg&3pUa?6)(+yt((_zUw%*JecO< z8yp!kY|I!E8^DsYgc!HsQtwYV#qf{7-%=%+*fnBOcxUUh@;nX7@*gFC!5Rg}|Ba=~ z^oUg)20n}EOMvMdJvLtx_nK(4!YzE2q6Q)`B~PVT|6|g5&SDL(#dt^Z3@jD%4bsZ; zU&Of2L1`@6`mOdzwBq+~$iCbEwEkiqQE#u8zDS!b8d*Geu6gn@de-T-nw_Yfv{OVw zjws!Il}4@IWM@yy?c`~q79EHUT=)9;K$e?c;Jh`6V~sfu8C5@A zM(l?wK!|uYRC)ae;&(NbJA_&7tWGWIw6s{x;_h*Pk>#X}!NX(0Y&=J#TzxT?HZY&7|_(M&Bj`8`zkh`2XuMfGyvy5??!thHzDs-NB{k=tBUjY2d oTNsUr@&@y!*}Ia46K!9Z#nDD$dxkC*dsj?^h;;b7V`y`K0ohb};s5{u literal 0 HcmV?d00001 diff --git a/tests/common/memcpy.c b/tests/common/memcpy.c new file mode 100644 index 00000000..235f54c0 --- /dev/null +++ b/tests/common/memcpy.c @@ -0,0 +1,83 @@ +#include "gdev_api.h" +#ifdef __KERNEL__ /* just for measurement */ +#define printf printk +#define gettimeofday(x, y) do_gettimeofday(x) +#include +#else /* just for measurement */ +#include +#include +#endif + +/* tvsub: ret = x - y. */ +static inline void tvsub(struct timeval *x, + struct timeval *y, + struct timeval *ret) +{ + ret->tv_sec = x->tv_sec - y->tv_sec; + ret->tv_usec = x->tv_usec - y->tv_usec; + if (ret->tv_usec < 0) { + ret->tv_sec--; + ret->tv_usec += 1000000; + } +} + +int gdev_test_memcpy(uint32_t *in, uint32_t *out, uint32_t size, + uint32_t chunk_size, int pipeline_count) +{ + gdev_handle_t *handle; + uint64_t data_addr; + struct timeval tv; + struct timeval tv_total_start, tv_total_end; + unsigned long total; + struct timeval tv_h2d_start, tv_h2d_end; + unsigned long h2d; + struct timeval tv_d2h_start, tv_d2h_end; + unsigned long d2h; + + gettimeofday(&tv_total_start, NULL); + + if (!(handle = gopen(0))) { + printf("gopen() failed.\n"); + return -1; + } + + if (gtune(handle, GDEV_TUNE_MEMCPY_CHUNK_SIZE, chunk_size)) { + printf("gtune() failed.\n"); + return -1; + } + if (gtune(handle, GDEV_TUNE_MEMCPY_PIPELINE_COUNT, pipeline_count)) { + printf("gtune() failed.\n"); + return -1; + } + + if (!(data_addr = gmalloc(handle, size))) { + printf("gmalloc() failed.\n"); + return -1; + } + + gettimeofday(&tv_h2d_start, NULL); + gmemcpy_to_device(handle, data_addr, in, size); + gettimeofday(&tv_h2d_end, NULL); + + + gettimeofday(&tv_d2h_start, NULL); + gmemcpy_from_device(handle, out, data_addr, size); + gettimeofday(&tv_d2h_end, NULL); + + gfree(handle, data_addr); + gclose(handle); + + gettimeofday(&tv_total_end, NULL); + + tvsub(&tv_h2d_end, &tv_h2d_start, &tv); + h2d = tv.tv_sec * 1000 + tv.tv_usec / 1000; + tvsub(&tv_d2h_end, &tv_d2h_start, &tv); + d2h = tv.tv_sec * 1000 + tv.tv_usec / 1000; + tvsub(&tv_total_end, &tv_total_start, &tv); + total = tv.tv_sec * 1000 + tv.tv_usec / 1000; + printf("%lu, ", h2d); + printf("%lu", d2h); + printf("\n"); + + return 0; +} diff --git a/tests/common/openclose.c b/tests/common/openclose.c new file mode 100644 index 00000000..faffcdbd --- /dev/null +++ b/tests/common/openclose.c @@ -0,0 +1,14 @@ +#include "gdev_api.h" + +int gdev_test_openclose(void) +{ + gdev_handle_t *handle; + + if (!(handle = gopen(0))) { + return -1; + } + + gclose(handle); + + return 0; +} diff --git a/tests/cuda/matrixmul/Makefile b/tests/cuda/matrixmul/Makefile new file mode 100644 index 00000000..62697ade --- /dev/null +++ b/tests/cuda/matrixmul/Makefile @@ -0,0 +1,13 @@ +# Makefile +TARGET = user_test +CC = gcc +NVCC = nvcc -arch sm_20 +LIBS = -lcuda +CFLAGS = -I /usr/local/cuda/include + +all: + #$(NVCC) main.c -o $(TARGET) $(CFLAGS) $(LIBS) + gcc main.c -o $(TARGET) $(CFLAGS) $(LIBS) + +clean: + rm -f $(TARGET) ./*~ diff --git a/tests/cuda/matrixmul/main.c b/tests/cuda/matrixmul/main.c new file mode 100644 index 00000000..eefc2c7e --- /dev/null +++ b/tests/cuda/matrixmul/main.c @@ -0,0 +1,194 @@ +#define PTX + +#include +#include +#include +#include +#include +#include + +/* tvsub: ret = x - y. */ +static inline void tvsub(struct timeval *x, + struct timeval *y, + struct timeval *ret) +{ + ret->tv_sec = x->tv_sec - y->tv_sec; + ret->tv_usec = x->tv_usec - y->tv_usec; + if (ret->tv_usec < 0) { + ret->tv_sec--; + ret->tv_usec += 1000000; + } +} + +int test_matrixmul(unsigned int n) +{ + int i; + CUresult res; + CUfunction function; + CUmodule module; + CUdeviceptr a_dev, b_dev, c_dev, n_dev; + unsigned int *a = (unsigned int *) malloc (n*n * sizeof(unsigned int)); + unsigned int *b = (unsigned int *) malloc (n*n * sizeof(unsigned int)); + unsigned int *c = (unsigned int *) malloc (n*n * sizeof(unsigned int)); + + printf("N = %d\n", n); + for (i = 0; i < n*n; i++) { + a[i] = i; + c[i] = 0xff; + if (i % (n + 1)) + b[i] = 0; + else + b[i] = 2; + } + + res = cuModuleLoad(&module, "./matrixmul_gpu.cubin"); + if (res != CUDA_SUCCESS) { + printf("cuModuleLoad() failed\n"); + return 0; + } + res = cuModuleGetFunction(&function, module, "_Z8multiplyPjS_S_S_"); + if (res != CUDA_SUCCESS) { + printf("cuModuleGetFunction() failed\n"); + return 0; + } + + cuFuncSetSharedSize(function, 0x40); + cuFuncSetBlockShape(function, n, 1, 1); + + cuMemAlloc(&a_dev, n*n * sizeof(unsigned int)); + cuMemcpyHtoD(a_dev, a, n*n * sizeof(unsigned int)); + if (res != CUDA_SUCCESS) + printf("cuMemcpyHtoD (1) failed: res = %u\n", res); + + cuMemAlloc(&b_dev, n*n * sizeof(unsigned int)); + cuMemcpyHtoD(b_dev, b, n*n * sizeof(unsigned int)); + if (res != CUDA_SUCCESS) + printf("cuMemcpyHtoD (2) failed: res = %u\n", res); + + cuMemAlloc(&c_dev, n*n * sizeof(unsigned int)); + cuMemcpyHtoD(c_dev, c, n*n * sizeof(unsigned int)); + if (res != CUDA_SUCCESS) + printf("cuMemcpyHtoD (3) failed: res = %u\n", res); + + cuMemAlloc(&n_dev, sizeof(unsigned int)); + cuMemcpyHtoD(n_dev, &n, sizeof(unsigned int)); + if (res != CUDA_SUCCESS) + printf("cuMemcpyHtoD (4) failed: res = %u\n", res); + + cuParamSeti(function, 0, a_dev); + cuParamSeti(function, 4, a_dev >> 32); + cuParamSeti(function, 8, b_dev); + cuParamSeti(function, 12, b_dev >> 32); + cuParamSeti(function, 16, c_dev); + cuParamSeti(function, 20, c_dev >> 32); + cuParamSeti(function, 24, n_dev); + cuParamSeti(function, 28, n_dev >> 32); + cuParamSetSize(function, 32); + + res = cuLaunchGrid(function, n, 1); + if (res != CUDA_SUCCESS) + printf("cuLaunchGrid failed: res = %u\n", res); + + cuMemcpyDtoH(a, a_dev, n*n * sizeof(unsigned int)); + if (res != CUDA_SUCCESS) + printf("cuMemcpyDtoH (1) failed: res = %u\n", res); + printf("A = "); + for (i = 0; i < n*n; i++) { + if (i % n == 0 && i != 0) + printf(" "); + printf("%d,", a[i]); + } + printf("\n"); + cuMemcpyDtoH(b, b_dev, n*n * sizeof(unsigned int)); + if (res != CUDA_SUCCESS) + printf("cuMemcpyDtoH (2) failed: res = %u\n", res); + printf("B = "); + for (i = 0; i < n*n; i++) { + if (i % n == 0 && i != 0) + printf(" "); + printf("%d,", b[i]); + } + printf("\n"); + cuMemcpyDtoH(c, c_dev, n*n * sizeof(unsigned int)); + if (res != CUDA_SUCCESS) + printf("cuMemcpyDtoH (3) failed: res = %u\n", res); + printf("C = "); + for (i = 0; i < n*n; i++) { + if (i % n == 0 && i != 0) + printf(" "); + printf("%d,", c[i]); + } + printf("\n"); + + cuMemFree(a_dev); + cuMemFree(b_dev); + cuMemFree(c_dev); + cuMemFree(n_dev); + + cuModuleUnload(module); + + free(a); + free(b); + free(c); + + return 0; +} + +int main(int argc, char *argv[]) +{ + CUresult res; + CUdevice dev; + CUcontext ctx; + CUevent event[2]; + + int count; + size_t vram; + int major, minor; + + unsigned int n = 3; + + if (argc > 1) + n = atoi(argv[1]); + + res = cuInit(0); + if (res != CUDA_SUCCESS) { + printf("cuInit failed: res = %u\n", res); + return 0; + } + + res = cuDeviceGet(&dev, 0); + if (res != CUDA_SUCCESS) { + printf("cuDeviceGet failed: res = %u\n", res); + return 0; + } + + res = cuDeviceGetCount(&count); + if (res != CUDA_SUCCESS) { + printf("cuDeviceGetCount failed: res = %u\n", res); + return 0; + } + + res = cuDeviceComputeCapability(&major, &minor, dev); + if (res != CUDA_SUCCESS) { + printf("cuDeviceComputeCapability failed: res = %u\n", res); + return 0; + } + + res = cuCtxCreate(&ctx, 0, dev); + if (res != CUDA_SUCCESS) { + printf("cuCtxCreate failed: res = %u\n", res); + return 0; + } + + test_matrixmul(n); + + res = cuCtxDestroy(ctx); + if (res != CUDA_SUCCESS) { + printf("cuCtxDestroy failed: res = %u\n", res); + return 0; + } + + printf("test finished\n"); + + return 0; +} diff --git a/tests/cuda/matrixmul/matrixmul_gpu.cubin b/tests/cuda/matrixmul/matrixmul_gpu.cubin new file mode 100644 index 0000000000000000000000000000000000000000..a220579004b7b1841730cd22617c1186eab44d16 GIT binary patch literal 2556 zcmbtW&ubGw6n>l8wrNdktOXOived+^{vtnbavq}$CFDV>mg^WJ>ln{R&ZJ|Dk% zBcLc(Rd7lGzJMa?WbSl3j^P*>PzJz&6fk^-jvxi#gogTJJ{&^?!)`H%lR72k%rX3| z0LCRySWh}QkMV#9L++yBR|SDEefXFB2!XJe_@`JWIj-`%!*NoAK*PbQ40-jx$2dW} z8j@WO-*60n64%RL#h4#|PVnbEd?BY59Tj}9{%yhkERduhF@4_te+s@=|Er)wObI?2 zO6lc)#h9P|Ex~u={rGo};eQkSEVj!+eDC;giI`Xau-NxWNfy@2hs46;1#{jkOk+*j zr5Wy*pCulZW~U3KM6p~nA<^<7VLn(i6I1uD%{(oc#ktbbmF$y=sfj6$DV873wkp0L z!A?oGLw3=T<==RJw!B~#%4YJvh|8nCUE>(sIobvQK7;ZTDrd{W8rsZhg|lxJP=s^pxes3DRG zd$($Tyj!`xO*_lSTeq^f4pF_X;cK17FV>-H;kuz;*A!fjsLt#FZK+H;SK#YV*FH5U z-jN#$<7wEuqz#3;BCt7b;d~}xljYtHBR<=-KJq-weu4X=Ur*=ie14gh$L2o0rZv!> zex4OfqJ~10t2M_ozrE<|IG-#UIr)6{2jMKwh`GKLbQ0xA@j^-lEZM9Xg{YIm1+ n!jbmybV9xZJCffHZVuId(BNG52oF1#?`#Kk_#6{FX(jI;yOSph literal 0 HcmV?d00001 diff --git a/tests/cuda/memcpy/Makefile b/tests/cuda/memcpy/Makefile new file mode 100644 index 00000000..62697ade --- /dev/null +++ b/tests/cuda/memcpy/Makefile @@ -0,0 +1,13 @@ +# Makefile +TARGET = user_test +CC = gcc +NVCC = nvcc -arch sm_20 +LIBS = -lcuda +CFLAGS = -I /usr/local/cuda/include + +all: + #$(NVCC) main.c -o $(TARGET) $(CFLAGS) $(LIBS) + gcc main.c -o $(TARGET) $(CFLAGS) $(LIBS) + +clean: + rm -f $(TARGET) ./*~ diff --git a/tests/cuda/memcpy/Makefile.pathscale b/tests/cuda/memcpy/Makefile.pathscale new file mode 100644 index 00000000..daad3d49 --- /dev/null +++ b/tests/cuda/memcpy/Makefile.pathscale @@ -0,0 +1,13 @@ +# Makefile +TARGET = user_test +CC = gcc +NVCC = nvcc -arch sm_20 +LIBS = -lenvyrt -ldrm +CFLAGS = -I /usr/local/cuda/include +SRC = $(wildcard ./*.cu) + +all: + $(CC) main.c -o $(TARGET) $(CFLAGS) $(LIBS) + +clean: + rm -f $(TARGET) ./*~ diff --git a/tests/cuda/memcpy/main.c b/tests/cuda/memcpy/main.c new file mode 100644 index 00000000..7479480d --- /dev/null +++ b/tests/cuda/memcpy/main.c @@ -0,0 +1,160 @@ +#define PTX + +#include +#include +#include +#include +#include +#include + +/* tvsub: ret = x - y. */ +static inline void tvsub(struct timeval *x, + struct timeval *y, + struct timeval *ret) +{ + ret->tv_sec = x->tv_sec - y->tv_sec; + ret->tv_usec = x->tv_usec - y->tv_usec; + if (ret->tv_usec < 0) { + ret->tv_sec--; + ret->tv_usec += 1000000; + } +} + +int gdev_test_memcpy(uint32_t *in, uint32_t *out, uint32_t size) +{ + CUresult res; + CUdevice dev; + CUcontext ctx; + CUdeviceptr data_addr; + struct timeval tv; + struct timeval tv_total_start, tv_total_end; + unsigned long total; + struct timeval tv_h2d_start, tv_h2d_end; + unsigned long h2d; + struct timeval tv_d2h_start, tv_d2h_end; + unsigned long d2h; + + gettimeofday(&tv_total_start, NULL); + + res = cuInit(0); + if (res != CUDA_SUCCESS) { + printf("cuInit failed: res = %u\n", res); + return 0; + } + + res = cuDeviceGet(&dev, 0); + if (res != CUDA_SUCCESS) { + printf("cuDeviceGet failed: res = %u\n", res); + return 0; + } + + res = cuCtxCreate(&ctx, 0, dev); + if (res != CUDA_SUCCESS) { + printf("cuCtxCreate failed: res = %u\n", res); + return 0; + } + + cuMemAlloc(&data_addr, size); + + gettimeofday(&tv_h2d_start, NULL); + res = cuMemcpyHtoD(data_addr, in, size); + gettimeofday(&tv_h2d_end, NULL); + + if (res != CUDA_SUCCESS) { + printf("cuMemcpyHtoD failed: res = %u\n", res); + return 0; + } + + gettimeofday(&tv_d2h_start, NULL); + res = cuMemcpyDtoH(out, data_addr, size); + gettimeofday(&tv_d2h_end, NULL); + + if (res != CUDA_SUCCESS) + printf("cuMemcpyDtoH failed: res = %u\n", res); + + cuMemFree(data_addr); + + res = cuCtxDestroy(ctx); + if (res != CUDA_SUCCESS) { + printf("cuCtxDestroy failed: res = %u\n", res); + return 0; + } + + gettimeofday(&tv_total_end, NULL); + + tvsub(&tv_h2d_end, &tv_h2d_start, &tv); + h2d = tv.tv_sec * 1000 + tv.tv_usec / 1000; + tvsub(&tv_d2h_end, &tv_d2h_start, &tv); + d2h = tv.tv_sec * 1000 + tv.tv_usec / 1000; + tvsub(&tv_total_end, &tv_total_start, &tv); + total = tv.tv_sec * 1000 + tv.tv_usec / 1000; + //printf("HtoD: %lu\n", h2d); + //printf("DtoH: %lu\n", d2h); + //printf("%lu\n", total - h2d - d2h); + //printf("Total = %lu ms\n", total); + + return 0; +} + +int main(int argc, char *argv[]) +{ + uint32_t *in, *out; + uint32_t size = 0x10000000; + uint32_t ch_size = 0x2000000; + int pl = 1; + int i, tmp; + + for (i = 1; i < argc; i++) { + if (strncmp(argv[i], "--chunk", (tmp = strlen("--chunk"))) == 0) { + if (argv[i][tmp] != '=') { + printf("option \"%s\" is invalid.\n", argv[i]); + exit(1); + } + sscanf(&argv[i][tmp+1], "%x", &ch_size); + } + else if (strncmp(argv[i], "--data", (tmp = strlen("--data"))) == 0) { + if (argv[i][tmp] != '=') { + printf("option \"%s\" is invalid.\n", argv[i]); + exit(1); + } + sscanf(&argv[i][tmp+1], "%x", &size); + } + else if (strncmp(argv[i], "--pl", (tmp = strlen("--pl"))) == 0) { + if (argv[i][tmp] != '=') { + printf("option \"%s\" is invalid.\n", argv[i]); + exit(1); + } + sscanf(&argv[i][tmp+1], "%d", &pl); + } + } + + printf("size = 0x%x\n", size); + printf("ch_size = 0x%x\n", ch_size); + in = (uint32_t *) malloc(size); + out = (uint32_t *) malloc(size); + for (i = 0; i < size / 4; i++) { + in[i] = i+1; + out[i] = 0; + } + + gdev_test_memcpy(in, out, size); + + for (i = 0; i < size / 4; i++) { + if (in[i] != out[i]) { + printf("in[%d] = %lu, out[%d] = %lu\n", + i, in[i], i, out[i]); + printf("Test failed.\n"); + goto end; + } + } + free(in); + free(out); + + return 0; + +end: + free(in); + free(out); + + return 0; +} diff --git a/tests/cuda/memcpy/simple_example1.cubin b/tests/cuda/memcpy/simple_example1.cubin new file mode 100644 index 0000000000000000000000000000000000000000..a1d8c8edd4114982d85e051e4462650d5d7b0d10 GIT binary patch literal 1264 zcmb7EF-yZx5WY02#+t#_f(jPurXZmph=W50?Ih?dh_=#dpeAC2sEb|P9UNQ)e}{vc zqd&o|;MzYRdY9Za@#QT&NWQ!8ecyZcn)iCYyVooj#)bt+6yO~U&ItxQ;4xP{Z^X~z!_uq_KA5!GKxGLZ@h`G^ zlesCb1wOf{1`|}G#!~xlBTsXxJ^ZkLo&5ylRsH+O>HKRf+$JLjQPRI~P3F|~JM5Qz zieB}D+duC|S5d2tnc(e3TnE?gSubq2dafV%5xCMe=OLICjb6ZYSX6`2!UU!`Ihm0J0HSy`El0%T_r;~-0w@JrC6DAaM zEPaH^Tz>xH5gw2oSRKB=06fGmc#N?IuY?cFb(-txyGDST3Bq#hSWR!MWWx+%9UL&1 z9IzG~_{A{rF9Am7aUB~*D_~XZ`0`L~mD3zc+B9u&knRSnG%h(6%*alPcp>GUrH&+f IW +#include +#include + +MODULE_LICENSE("Dual BSD/GPL"); +MODULE_DESCRIPTION("Gdev Kernel Test"); +MODULE_AUTHOR("Shinpei Kato"); + +int gdev_test_loadstore(void); + +struct task_struct *test_thread = NULL; + +static void test_thread_func(void *__data) +{ + int ret = gdev_test_loadstore(); + if (ret < 0) + printk("Test failed\n"); + else + printk("Test passed\n"); + while (!kthread_should_stop()) { + schedule_timeout(1000); + } +} + +static int __init gdev_test_init(void) +{ + test_thread = kthread_create((void*)test_thread_func, NULL, "gdevtest"); + /*sched_setscheduler(test_thread, SCHED_FIFO, &sp);*/ + wake_up_process(test_thread); + return 0; +} + +static void __exit gdev_test_exit(void) +{ + if (test_thread) { + kthread_stop(test_thread); + } +} + +module_init(gdev_test_init); +module_exit(gdev_test_exit); diff --git a/tests/kernel/memcpy/Makefile b/tests/kernel/memcpy/Makefile new file mode 100644 index 00000000..0e92fa59 --- /dev/null +++ b/tests/kernel/memcpy/Makefile @@ -0,0 +1,38 @@ +TARGET = kernel_test +OBJS = main.o memcpy.o +GDEVDIR = /usr/local/gdev +GDEVINC = $(GDEVDIR)/include +DRMINC = /lib/modules/$(shell uname -r)/source/include/drm +CPPFLAGS += -Wno-strict-prototypes + +# If KERNELRELEASE is define, we have been invoked from the +# kernel build system and can use its languages. +ifneq ($(KERNELRELEASE),) + obj-m := $(TARGET).o + $(TARGET)-objs := $(OBJS) + EXTRA_CFLAGS := -I$(GDEVINC) -I$(DRMINC) + +# Otherwise we were called directly from the command line; +# invoke the kernel build system +else + KERNELDIR ?= /lib/modules/$(shell uname -r)/build + EXTRA_CFLAGS := -I$(GDEVINC) -I$(DRMINC) + +all: + @cp -f $(GDEVDIR)/Module.symvers . + $(MAKE) -C $(KERNELDIR) M=$(PWD) modules + +$(TARGET).o: $(OBJS) + $(LD) $(LD_RFLAG) -r -o $@ $(OBJS) + +clean: + @rm -fr .tmp* .*.o.cmd *.mod.* *.ko *.o .$(TARGET)* modules.order Module.* *~ + +.PHONY:install +install: + @./script/install + +.PHONY:uninstall +uninstall: + @./script/uninstall +endif diff --git a/tests/kernel/memcpy/main.c b/tests/kernel/memcpy/main.c new file mode 100644 index 00000000..5c14e5f6 --- /dev/null +++ b/tests/kernel/memcpy/main.c @@ -0,0 +1,65 @@ +#include +#include +#include +#include + +MODULE_LICENSE("Dual BSD/GPL"); +MODULE_DESCRIPTION("Gdev Kernel Test"); +MODULE_AUTHOR("Shinpei Kato"); + +int gdev_test_memcpy(uint32_t *, uint32_t *, uint32_t); + +struct task_struct *test_thread = NULL; + +static void test_thread_func(void *__data) +{ + int i; + uint32_t size = 0x400000; /* 4MB */ + uint32_t *in, *out; + +start: + in = (uint32_t *) vmalloc(size); + out = (uint32_t *) vmalloc(size); + + for (i = 0; i < size / 4; i++) { + in[i] = i; + out[i] = 0; + } + + gdev_test_memcpy(in, out, size); + + for (i = 0; i < size / 4; i++) { + if (in[i] != out[i]) { + printk("in[%d] = %u, out[%d] = %u\n", i, in[i], i, out[i]); + printk("Test failed.\n"); + goto end; + } + } + printk("Test passed.\n"); +end: + + vfree(in); + vfree(out); + + if (size != 0x10000000) { + size *= 2; + goto start; + } +} + +static int __init gdev_test_init(void) +{ + test_thread = kthread_create((void*)test_thread_func, NULL, "gdevtest"); + wake_up_process(test_thread); + return 0; +} + +static void __exit gdev_test_exit(void) +{ + if (test_thread) { + kthread_stop(test_thread); + } +} + +module_init(gdev_test_init); +module_exit(gdev_test_exit); diff --git a/tests/kernel/memcpy/memcpy.c b/tests/kernel/memcpy/memcpy.c new file mode 120000 index 00000000..40ba5ae1 --- /dev/null +++ b/tests/kernel/memcpy/memcpy.c @@ -0,0 +1 @@ +../../common/memcpy.c \ No newline at end of file diff --git a/tests/user/loadstore/Makefile b/tests/user/loadstore/Makefile new file mode 100644 index 00000000..4a895d10 --- /dev/null +++ b/tests/user/loadstore/Makefile @@ -0,0 +1,22 @@ +# Makefile + +CC = gcc +CFLAGS = -lgdev -I/usr/local/gdev/include + +SRC = $(wildcard ./*.c) +OBJS = $(patsubst %.c,%.o,$(SRC)) +ZOMBIE = $(wildcard *~) + +.PHONY: clean user_test + +all: user_test + +user_test: $(OBJS) + $(CC) -o $@ $^ $(CFLAGS) + +%.o:%.c + $(CC) -c $^ -o $@ $(CFLAGS) + +clean: + rm -f user_test $(OBJS) $(ZOMBIE) + diff --git a/tests/user/loadstore/loadstore.c b/tests/user/loadstore/loadstore.c new file mode 120000 index 00000000..a022d56b --- /dev/null +++ b/tests/user/loadstore/loadstore.c @@ -0,0 +1 @@ +../../common/loadstore.c \ No newline at end of file diff --git a/tests/user/loadstore/main.c b/tests/user/loadstore/main.c new file mode 100644 index 00000000..21cc67cb --- /dev/null +++ b/tests/user/loadstore/main.c @@ -0,0 +1,13 @@ +#include + +int gdev_test_loadstore(void); + +int main(int argc, char *argv[]) +{ + int ret = gdev_test_loadstore(); + if (ret < 0) + printf("Test failed\n"); + else + printf("Test passed\n"); + return 0; +} diff --git a/tests/user/matrixadd/Makefile b/tests/user/matrixadd/Makefile new file mode 100644 index 00000000..4a895d10 --- /dev/null +++ b/tests/user/matrixadd/Makefile @@ -0,0 +1,22 @@ +# Makefile + +CC = gcc +CFLAGS = -lgdev -I/usr/local/gdev/include + +SRC = $(wildcard ./*.c) +OBJS = $(patsubst %.c,%.o,$(SRC)) +ZOMBIE = $(wildcard *~) + +.PHONY: clean user_test + +all: user_test + +user_test: $(OBJS) + $(CC) -o $@ $^ $(CFLAGS) + +%.o:%.c + $(CC) -c $^ -o $@ $(CFLAGS) + +clean: + rm -f user_test $(OBJS) $(ZOMBIE) + diff --git a/tests/user/matrixadd/main.c b/tests/user/matrixadd/main.c new file mode 100644 index 00000000..aab5d19d --- /dev/null +++ b/tests/user/matrixadd/main.c @@ -0,0 +1,33 @@ +#include +#include +#include + +int gdev_test_matrixadd(uint32_t *a, uint32_t *b, uint32_t *c, int n); + +int main(int argc, char *argv[]) +{ + int ret; + int n; + uint32_t *a, *b, *c; + + if(argc != 2) { + printf("Invalid arguments\n"); + return 0; + } + + n = atoi(argv[1]); + a = malloc(n * n * sizeof(uint32_t)); + b = malloc(n * n * sizeof(uint32_t)); + c = malloc(n * n * sizeof(uint32_t)); + + if (gdev_test_matrixadd(a, b, c, n)) + printf("Test failed.\n"); + else + printf("Test passed.\n"); +end: + free(a); + free(b); + free(c); + + return 0; +} diff --git a/tests/user/matrixadd/matrixadd.c b/tests/user/matrixadd/matrixadd.c new file mode 120000 index 00000000..7f1cc8b4 --- /dev/null +++ b/tests/user/matrixadd/matrixadd.c @@ -0,0 +1 @@ +../../common/matrixadd.c \ No newline at end of file diff --git a/tests/user/memcpy/Makefile b/tests/user/memcpy/Makefile new file mode 100644 index 00000000..4a895d10 --- /dev/null +++ b/tests/user/memcpy/Makefile @@ -0,0 +1,22 @@ +# Makefile + +CC = gcc +CFLAGS = -lgdev -I/usr/local/gdev/include + +SRC = $(wildcard ./*.c) +OBJS = $(patsubst %.c,%.o,$(SRC)) +ZOMBIE = $(wildcard *~) + +.PHONY: clean user_test + +all: user_test + +user_test: $(OBJS) + $(CC) -o $@ $^ $(CFLAGS) + +%.o:%.c + $(CC) -c $^ -o $@ $(CFLAGS) + +clean: + rm -f user_test $(OBJS) $(ZOMBIE) + diff --git a/tests/user/memcpy/main.c b/tests/user/memcpy/main.c new file mode 100644 index 00000000..f69c3acb --- /dev/null +++ b/tests/user/memcpy/main.c @@ -0,0 +1,76 @@ +#include +#include +#include +#include +#include + +#define DATA_END 0x10000000 /* 256MB */ +#define DATA_START DATA_END // 0x400000 /* 4MB */ +#define CHUNK_END 0x2000000 /* 32MB */ +#define CHUNK_START 0x10000 /* 64KB */ +#define PIPELINE_END 4 +#define PIPELINE_START 4 + +int gdev_test_memcpy(uint32_t *in, uint32_t *out, uint32_t size, + uint32_t chunk_size, int pipeline_count); + +int main(int argc, char *argv[]) +{ + uint32_t *in, *out; + uint32_t size = 0x10000000; + uint32_t ch_size = 0x40000; /* 0x200000 is best */ + int pl = 2; + int i, tmp; + + for (i = 1; i < argc; i++) { + if (strncmp(argv[i], "--chunk", (tmp = strlen("--chunk"))) == 0) { + if (argv[i][tmp] != '=') { + printf("option \"%s\" is invalid.\n", argv[i]); + exit(1); + } + sscanf(&argv[i][tmp+1], "%x", &ch_size); + } + else if (strncmp(argv[i], "--data", (tmp = strlen("--data"))) == 0) { + if (argv[i][tmp] != '=') { + printf("option \"%s\" is invalid.\n", argv[i]); + exit(1); + } + sscanf(&argv[i][tmp+1], "%x", &size); + } + else if (strncmp(argv[i], "--pl", (tmp = strlen("--pl"))) == 0) { + if (argv[i][tmp] != '=') { + printf("option \"%s\" is invalid.\n", argv[i]); + exit(1); + } + sscanf(&argv[i][tmp+1], "%d", &pl); + } + } + + in = (uint32_t *) malloc(size); + out = (uint32_t *) malloc(size); + for (i = 0; i < size / 4; i++) { + in[i] = i+1; + out[i] = 0; + } + + gdev_test_memcpy(in, out, size, ch_size, pl); + + for (i = 0; i < size / 4; i++) { + if (in[i] != out[i]) { + printf("in[%d] = %lu, out[%d] = %lu\n", + i, in[i], i, out[i]); + printf("Test failed.\n"); + goto end; + } + } + free(in); + free(out); + + return 0; + +end: + free(in); + free(out); + + return 0; +} diff --git a/tests/user/memcpy/memcpy.c b/tests/user/memcpy/memcpy.c new file mode 120000 index 00000000..40ba5ae1 --- /dev/null +++ b/tests/user/memcpy/memcpy.c @@ -0,0 +1 @@ +../../common/memcpy.c \ No newline at end of file diff --git a/tests/user/openclose/Makefile b/tests/user/openclose/Makefile new file mode 100644 index 00000000..4a895d10 --- /dev/null +++ b/tests/user/openclose/Makefile @@ -0,0 +1,22 @@ +# Makefile + +CC = gcc +CFLAGS = -lgdev -I/usr/local/gdev/include + +SRC = $(wildcard ./*.c) +OBJS = $(patsubst %.c,%.o,$(SRC)) +ZOMBIE = $(wildcard *~) + +.PHONY: clean user_test + +all: user_test + +user_test: $(OBJS) + $(CC) -o $@ $^ $(CFLAGS) + +%.o:%.c + $(CC) -c $^ -o $@ $(CFLAGS) + +clean: + rm -f user_test $(OBJS) $(ZOMBIE) + diff --git a/tests/user/openclose/main.c b/tests/user/openclose/main.c new file mode 100644 index 00000000..72c009b1 --- /dev/null +++ b/tests/user/openclose/main.c @@ -0,0 +1,12 @@ +#include + +int gdev_test_openclose(void); + +int main(int argc, char *argv[]) +{ + if (gdev_test_openclose()) + printf("Test failed.\n"); + else + printf("Test passed.\n"); + return 0; +} diff --git a/tests/user/openclose/main.c~ b/tests/user/openclose/main.c~ new file mode 100644 index 00000000..2aeb29f8 --- /dev/null +++ b/tests/user/openclose/main.c~ @@ -0,0 +1,105 @@ +#include +#include +#include +#include +#include + +#define DATA_END 0x10000000 /* 256MB */ +#define DATA_START DATA_END // 0x400000 /* 4MB */ +#define CHUNK_END 0x2000000 /* 32MB */ +#define CHUNK_START 0x10000 /* 64KB */ +#define PIPELINE_END 4 +#define PIPELINE_START 4 + +int gdev_test_memcpy(uint32_t *in, uint32_t *out, uint32_t size, + uint32_t chunk_size, int pipeline_count); + +int main(int argc, char *argv[]) +{ + uint32_t *in, *out; + uint32_t size = 0x10000000; + uint32_t ch_size = 0x40000; + int pl = 1; + int i, tmp; + + for (i = 1; i < argc; i++) { + if (strncmp(argv[i], "--chunk", (tmp = strlen("--chunk"))) == 0) { + if (argv[i][tmp] != '=') { + printf("option \"%s\" is invalid.\n", argv[i]); + exit(1); + } + sscanf(&argv[i][tmp+1], "%x", &ch_size); + } + else if (strncmp(argv[i], "--data", (tmp = strlen("--data"))) == 0) { + if (argv[i][tmp] != '=') { + printf("option \"%s\" is invalid.\n", argv[i]); + exit(1); + } + sscanf(&argv[i][tmp+1], "%x", &size); + } + else if (strncmp(argv[i], "--pl", (tmp = strlen("--pl"))) == 0) { + if (argv[i][tmp] != '=') { + printf("option \"%s\" is invalid.\n", argv[i]); + exit(1); + } + sscanf(&argv[i][tmp+1], "%d", &pl); + } + } + +#if 1 + printf("size = 0x%x\n", size); + printf("ch_size = 0x%x\n", ch_size); + in = (uint32_t *) malloc(size); + out = (uint32_t *) malloc(size); + for (i = 0; i < size / 4; i++) { + in[i] = i+1; + out[i] = 0; + } + + gdev_test_memcpy(in, out, size, ch_size, pl); + + for (i = 0; i < size / 4; i++) { + if (in[i] != out[i]) { + printf("in[%d] = %lu, out[%d] = %lu\n", + i, in[i], i, out[i]); + printf("Test failed.\n"); + goto end; + } + } + free(in); + free(out); +#else + for (size = DATA_START; size <= DATA_END; size *= 2) { + for (ch_size = CHUNK_START; ch_size <= CHUNK_END; ch_size *= 2) { + for (pl = PIPELINE_START; pl <= PIPELINE_END; pl *= 2) { + in = (uint32_t *) malloc(size); + out = (uint32_t *) malloc(size); + for (i = 0; i < size / 4; i++) { + in[i] = i; + out[i] = 0; + } + + gdev_test_memcpy(in, out, size, ch_size, pl); + + for (i = 0; i < size / 4; i++) { + if (in[i] != out[i]) { + printf("in[%d] = %lu, out[%d] = %lu\n", + i, in[i], i, out[i]); + printf("Test failed.\n"); + goto end; + } + } + free(in); + free(out); + } + } + } +#endif + return 0; + +end: + free(in); + free(out); + + return 0; +} diff --git a/tests/user/openclose/main.o b/tests/user/openclose/main.o new file mode 100644 index 0000000000000000000000000000000000000000..ed3f07c728bf513e4483d4a1b552a133e5763237 GIT binary patch literal 1656 zcmb_cL2FY%5T2J;TaAgt;z6y*^PsfFEJ?LuJxDZYa}W=~;xXMOTU*S_3wc|Kf_M;x z+{9nt&+ulzlRrc#=s|BD3U%h~PP<*>MI6|j`M#OinYTO1t9uXb=YjxO0=Nx_h*^Mj zhpc6E4T_M5wZ`ac4QSoP4?OSBT$W;xZe{S*TzO>MO{2QpSv;(thlhtSnedxzC5&c4m@O*uB1bGUqt z_}yc)0}PFVlc=dqb~mWcTK*#-nRW?l`>~I0zTf}Y#^1D>72iMOCK~>ol5gD(1iur# zALVjB^QV#X?;a`mMH`AV>R|W#C+zo5!5?f>kxeKdcLJARpSVf&$9Dc`zFhI^yFS;Z zxGDI#?{aL16JLz_nA8dJlWv%J+aw=sbqF&aV_cO1P@7t0=r0)$7sPwJ2QP((N!wO~GroRg!TtetN(On5*o0*Q7h_&7kmmq6T_DRYngDsdj2oQaf2js@3myb&pxE zZ?xh9Yne$~k4fd}dat=VNV^(a{|^g!6SQ{P+bp*8{GOcHl%pY+`0^R}@DxU(sBmxC~e^LxjLK4V~eRJifz*FULt zB*(U>8N1*NGo0<8Kg(>=`H8Jxaojckd^hH5KPYgP-_Svf+Dzf#aPK9>H}!)Si+gPHmxKdMGMBTG@Cj&*SG14n*fElwaXrPeaB72t;eoV)xV>G6Ge{^s3uUGxmyERB8YeYnwyymGK z3t+pin-Su#R$2yED>cb5U2DODDf>MMKg#pJZJg)2c&w{whVv%+$w8R9DV?Epgah+1ZO43FI{hAdGGsPUn>tCot?j3}JvjxracHk{`^>Belh zeSbJ(!|m%sAG+n89ERiMa!k$1eTc0O{oH$gX49c^pO{${$F*jq29D%D3UTAw4BDzL zl4&~MxFqE-kxZ%I$Vqt*$u#Y6j6-g`-I4w6vwHR&edyggyE{8BKD%CDu`TY z1DX6W4F54QLOJQf<$o&k3H^nf>7KbHQyQ_ieR}r#UNSuX*fi`!<_mA+uqDCm@8tIN zsR@$KeeBVPrd;~wD`|gE&B```o6EWMZ28+TnpyG-X*67ZmRvSpNxk#S^4Gw+DBLp# z&-e871Zq~Ez%7v9V`FZ_p}1z+4gCD==o`pshps}oLZz01Ib>P zJYC?K9}ztp_g@KSBmQgp$%e}=p9r2@^=l%)CxcnjemN@tB8Or}dM2aqGZutEXVihsgyrEHpEzcUoEYRU$-ZG;R8N!m)TX60n2;TJI2G zyTbFi)u3hg_n{k112F~~0eu(r1gMEo{sAcMy?w36$%iQ~` zsUM0@`Q%_%c!vPdXf{x@q`5NVv@oeTDeXbj7FuL>pRH0d@2?-;pGguFa%;He-!&#Y zmdty|sN0g~!-m=`7Ln%}vCEYFfTB!jW1u#u_9ed8kVNy(K^^~MslrFqxxn~wCDYhZ z<9PEdaaP7~TKA*uF@#d)@wua9UFntk|DEvrlQYn#%QXo#DY{M3rxYdS_SV+V`c~tO zV~uZPpeeB4w_$x_8PAXShGs zjetpXgG)g6ZS{jg8cxan{%FFKBl*8wR=}O+3eQvF)*zuNfc6G^<9Wr{r@&O=&;Ipp z4O0HS*e9j@r7X`%j^4ZM{#)Fd#J8vpX@9Xdr+*uicQMB~e#or>q4h0^XtszbSCrS2 z62(q13-D)uUiYI4@TnWFfDN(i&+G9iV6^7hpZAdowGr^X0TbDrr_`a z%5gY{Q7~l6{=DxTFA?8)|0f*&ypN44{}A-l zD1X|Uo&GNaqr7N*sqy>qv?IQywQ^;iD4jWW|5~+=)T#m7Z8rw5x}AMr{kFqDr2Iq5 zpXVWW!|%B)f7jv9=gcXZ)M)hGVs9Luu`w`|Kac--r3OieapnJrl=2rIKSs`gvHSCP zB!6G7WkW@s@qgs-_j)yH=~aPFDL*F8_&F#jKA(I1z0Kd@&hc{kUvT)-n=7>mW%!@` ze*;^4e0po8c2W5|<2mKau%)@j`SZEO^?)(z9F6BE`*U7bp|i*5@0|hl;=uN@6I@tk z`WJ^kzc&mjf8M`J`QLQ-kE{2NapmuP-cI?B%8BoPLixY0{P{ke@mc;*#b3{WqU`US ze`+}8n33rs{5iIAmE@X=f8P#*XMcuC=C#8Z(a>T`3aJN2b%J&H^SJZAIuBT}__>EH z|A!r&JL6kc#jhU9)~(G^dXO=nlXj&Cneh2nh?mX2uNLCvV$`kKA<26%TlpNaD?K=A z`FttFy&_bm*&)e$P{BD~6rV46pSL@Ciqtnq@4?Q``*NXu)odNI5HC^>k^R(QU)1cT zlJ{UY=Y7wv^k8=JepZOrp-vdGLz4H1#n^X>;Y+Ze6vH1t-LM$`;B4JPcC0QQyzTS) zF2t7!Ublt#LxR_1A->!$O5R!rRpKReez5_quQJrBSY}!e#)Zn0a~vL#_}p=zeaMBc zIOjOD19yumG46=_jI__^&+F!p!gFe$;q^GE`ten0;PS0h{wH8U`Hwrs|CRGP_d@O=dRzQCG5Wg ze38hnYd)XO0Iw}_zds~Rn1_eGM2jWo^wWLkW%}s(7Ml3Q& zQnRqWRU?`H{v#ZxeP^2tvu#hy6YT~|6o&bH6!}#vqfm(%xl&nLR;VfO?ZI7JTY|=} zZQJ&?cN(27TZ8SCKYctK;Z!PoMAn}R09pDLM%&XnTb}4>74$94wQ8%N-JQ-@Rc}=R zR}QwJD^WP7s<@`vi`}Yv?kto$j5>B9fk-T2WKfPn_5~?L(n+H)oQT9xk+%x->hbVU g$s#=EEGq_7={HQ2`i$9eLXVDmysFb%HGApyZ*`Q(_y7O^ literal 0 HcmV?d00001 diff --git a/traces/matrix_mul_nva3_dedmaed b/traces/matrix_mul_nva3_dedmaed new file mode 100644 index 00000000..ed4656e8 --- /dev/null +++ b/traces/matrix_mul_nva3_dedmaed @@ -0,0 +1,5510 @@ +00040060 size 1, subchannel 0 (0x0), offset 0x0060, increment +5c0000c5 OBJ0.0x60 +00044000 size 1, subchannel 2 (0x0), offset 0x0000, increment +5c0000d2 NVA3_COMPUTE mapped to subchannel 2 +000442a0 size 1, subchannel 2 (0x5c0000d2), offset 0x02a0, increment +00000001 NVA3_COMPUTE.UNK02A0 = 0x1 +000441bc size 1, subchannel 2 (0x5c0000d2), offset 0x01bc, increment +5c0000c5 NVA3_COMPUTE.DMA_STACK = 0x5c0000c5 +00044218 size 1, subchannel 2 (0x5c0000d2), offset 0x0218, increment +00000000 NVA3_COMPUTE.STACK_ADDRESS_HIGH = 0 +0004421c size 1, subchannel 2 (0x5c0000d2), offset 0x021c, increment +40a60000 NVA3_COMPUTE.STACK_ADDRESS_LOW = 0x40a60000 +00044220 size 1, subchannel 2 (0x5c0000d2), offset 0x0220, increment +0000000b NVA3_COMPUTE.STACK_SIZE_LOG = 11 +000441b8 size 1, subchannel 2 (0x5c0000d2), offset 0x01b8, increment +5c0000c5 NVA3_COMPUTE.DMA_LOCAL = 0x5c0000c5 +000441a4 size 1, subchannel 2 (0x5c0000d2), offset 0x01a4, increment +5c0000c5 NVA3_COMPUTE.DMA_QUERY = 0x5c0000c5 +000443ac size 1, subchannel 2 (0x5c0000d2), offset 0x03ac, increment +00010001 NVA3_COMPUTE.BLOCKDIM_XY = { X = 1 | Y = 1 } +000443b0 size 1, subchannel 2 (0x5c0000d2), offset 0x03b0, increment +00000001 NVA3_COMPUTE.BLOCKDIM_Z = 1 +000443a8 size 1, subchannel 2 (0x5c0000d2), offset 0x03a8, increment +00000040 NVA3_COMPUTE.SHARED_SIZE = 0x40 +000442b4 size 1, subchannel 2 (0x5c0000d2), offset 0x02b4, increment +00010001 NVA3_COMPUTE.BLOCK_ALLOC = { THREADS = 1 | BARRIERS = 1 } +000442c0 size 1, subchannel 2 (0x5c0000d2), offset 0x02c0, increment +00000001 NVA3_COMPUTE.CP_REG_ALLOC_TEMP = 0x1 +00044290 size 1, subchannel 2 (0x5c0000d2), offset 0x0290, increment +00000001 NVA3_COMPUTE.UNK0290 = TRUE +000442b8 size 1, subchannel 2 (0x5c0000d2), offset 0x02b8, increment +00000001 NVA3_COMPUTE.LANES32_ENABLE = TRUE +000443b8 size 1, subchannel 2 (0x5c0000d2), offset 0x03b8, increment +00000002 NVA3_COMPUTE.REG_MODE = STRIPED +000443a4 size 1, subchannel 2 (0x5c0000d2), offset 0x03a4, increment +00010001 NVA3_COMPUTE.GRIDDIM = { X = 1 | Y = 1 } +00044384 size 1, subchannel 2 (0x5c0000d2), offset 0x0384, increment +00000100 NVA3_COMPUTE.UNK0384 = 0x100 +000441a0 size 1, subchannel 2 (0x5c0000d2), offset 0x01a0, increment +5c0000c5 NVA3_COMPUTE.DMA_GLOBAL = 0x5c0000c5 +00044400 size 1, subchannel 2 (0x5c0000d2), offset 0x0400, increment +00000000 NVA3_COMPUTE.GLOBAL[0].ADDRESS_HIGH = 0 +00044404 size 1, subchannel 2 (0x5c0000d2), offset 0x0404, increment +00000000 NVA3_COMPUTE.GLOBAL[0].ADDRESS_LOW = 0 +0004440c size 1, subchannel 2 (0x5c0000d2), offset 0x040c, increment +00000000 NVA3_COMPUTE.GLOBAL[0].LIMIT = 0 +00044410 size 1, subchannel 2 (0x5c0000d2), offset 0x0410, increment +00000001 NVA3_COMPUTE.GLOBAL[0].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +00044420 size 1, subchannel 2 (0x5c0000d2), offset 0x0420, increment +00000000 NVA3_COMPUTE.GLOBAL[0x1].ADDRESS_HIGH = 0 +00044424 size 1, subchannel 2 (0x5c0000d2), offset 0x0424, increment +00000000 NVA3_COMPUTE.GLOBAL[0x1].ADDRESS_LOW = 0 +0004442c size 1, subchannel 2 (0x5c0000d2), offset 0x042c, increment +00000000 NVA3_COMPUTE.GLOBAL[0x1].LIMIT = 0 +00044430 size 1, subchannel 2 (0x5c0000d2), offset 0x0430, increment +00000001 NVA3_COMPUTE.GLOBAL[0x1].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +00044440 size 1, subchannel 2 (0x5c0000d2), offset 0x0440, increment +00000000 NVA3_COMPUTE.GLOBAL[0x2].ADDRESS_HIGH = 0 +00044444 size 1, subchannel 2 (0x5c0000d2), offset 0x0444, increment +00000000 NVA3_COMPUTE.GLOBAL[0x2].ADDRESS_LOW = 0 +0004444c size 1, subchannel 2 (0x5c0000d2), offset 0x044c, increment +00000000 NVA3_COMPUTE.GLOBAL[0x2].LIMIT = 0 +00044450 size 1, subchannel 2 (0x5c0000d2), offset 0x0450, increment +00000001 NVA3_COMPUTE.GLOBAL[0x2].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +00044460 size 1, subchannel 2 (0x5c0000d2), offset 0x0460, increment +00000000 NVA3_COMPUTE.GLOBAL[0x3].ADDRESS_HIGH = 0 +00044464 size 1, subchannel 2 (0x5c0000d2), offset 0x0464, increment +00000000 NVA3_COMPUTE.GLOBAL[0x3].ADDRESS_LOW = 0 +0004446c size 1, subchannel 2 (0x5c0000d2), offset 0x046c, increment +00000000 NVA3_COMPUTE.GLOBAL[0x3].LIMIT = 0 +00044470 size 1, subchannel 2 (0x5c0000d2), offset 0x0470, increment +00000001 NVA3_COMPUTE.GLOBAL[0x3].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +00044480 size 1, subchannel 2 (0x5c0000d2), offset 0x0480, increment +00000000 NVA3_COMPUTE.GLOBAL[0x4].ADDRESS_HIGH = 0 +00044484 size 1, subchannel 2 (0x5c0000d2), offset 0x0484, increment +00000000 NVA3_COMPUTE.GLOBAL[0x4].ADDRESS_LOW = 0 +0004448c size 1, subchannel 2 (0x5c0000d2), offset 0x048c, increment +00000000 NVA3_COMPUTE.GLOBAL[0x4].LIMIT = 0 +00044490 size 1, subchannel 2 (0x5c0000d2), offset 0x0490, increment +00000001 NVA3_COMPUTE.GLOBAL[0x4].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +000444a0 size 1, subchannel 2 (0x5c0000d2), offset 0x04a0, increment +00000000 NVA3_COMPUTE.GLOBAL[0x5].ADDRESS_HIGH = 0 +000444a4 size 1, subchannel 2 (0x5c0000d2), offset 0x04a4, increment +00000000 NVA3_COMPUTE.GLOBAL[0x5].ADDRESS_LOW = 0 +000444ac size 1, subchannel 2 (0x5c0000d2), offset 0x04ac, increment +00000000 NVA3_COMPUTE.GLOBAL[0x5].LIMIT = 0 +000444b0 size 1, subchannel 2 (0x5c0000d2), offset 0x04b0, increment +00000001 NVA3_COMPUTE.GLOBAL[0x5].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +000444c0 size 1, subchannel 2 (0x5c0000d2), offset 0x04c0, increment +00000000 NVA3_COMPUTE.GLOBAL[0x6].ADDRESS_HIGH = 0 +000444c4 size 1, subchannel 2 (0x5c0000d2), offset 0x04c4, increment +00000000 NVA3_COMPUTE.GLOBAL[0x6].ADDRESS_LOW = 0 +000444cc size 1, subchannel 2 (0x5c0000d2), offset 0x04cc, increment +00000000 NVA3_COMPUTE.GLOBAL[0x6].LIMIT = 0 +000444d0 size 1, subchannel 2 (0x5c0000d2), offset 0x04d0, increment +00000001 NVA3_COMPUTE.GLOBAL[0x6].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +000444e0 size 1, subchannel 2 (0x5c0000d2), offset 0x04e0, increment +00000000 NVA3_COMPUTE.GLOBAL[0x7].ADDRESS_HIGH = 0 +000444e4 size 1, subchannel 2 (0x5c0000d2), offset 0x04e4, increment +00000000 NVA3_COMPUTE.GLOBAL[0x7].ADDRESS_LOW = 0 +000444ec size 1, subchannel 2 (0x5c0000d2), offset 0x04ec, increment +00000000 NVA3_COMPUTE.GLOBAL[0x7].LIMIT = 0 +000444f0 size 1, subchannel 2 (0x5c0000d2), offset 0x04f0, increment +00000001 NVA3_COMPUTE.GLOBAL[0x7].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +00044500 size 1, subchannel 2 (0x5c0000d2), offset 0x0500, increment +00000000 NVA3_COMPUTE.GLOBAL[0x8].ADDRESS_HIGH = 0 +00044504 size 1, subchannel 2 (0x5c0000d2), offset 0x0504, increment +00000000 NVA3_COMPUTE.GLOBAL[0x8].ADDRESS_LOW = 0 +0004450c size 1, subchannel 2 (0x5c0000d2), offset 0x050c, increment +00000000 NVA3_COMPUTE.GLOBAL[0x8].LIMIT = 0 +00044510 size 1, subchannel 2 (0x5c0000d2), offset 0x0510, increment +00000001 NVA3_COMPUTE.GLOBAL[0x8].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +00044520 size 1, subchannel 2 (0x5c0000d2), offset 0x0520, increment +00000000 NVA3_COMPUTE.GLOBAL[0x9].ADDRESS_HIGH = 0 +00044524 size 1, subchannel 2 (0x5c0000d2), offset 0x0524, increment +00000000 NVA3_COMPUTE.GLOBAL[0x9].ADDRESS_LOW = 0 +0004452c size 1, subchannel 2 (0x5c0000d2), offset 0x052c, increment +00000000 NVA3_COMPUTE.GLOBAL[0x9].LIMIT = 0 +00044530 size 1, subchannel 2 (0x5c0000d2), offset 0x0530, increment +00000001 NVA3_COMPUTE.GLOBAL[0x9].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +00044540 size 1, subchannel 2 (0x5c0000d2), offset 0x0540, increment +00000000 NVA3_COMPUTE.GLOBAL[0xa].ADDRESS_HIGH = 0 +00044544 size 1, subchannel 2 (0x5c0000d2), offset 0x0544, increment +00000000 NVA3_COMPUTE.GLOBAL[0xa].ADDRESS_LOW = 0 +0004454c size 1, subchannel 2 (0x5c0000d2), offset 0x054c, increment +00000000 NVA3_COMPUTE.GLOBAL[0xa].LIMIT = 0 +00044550 size 1, subchannel 2 (0x5c0000d2), offset 0x0550, increment +00000001 NVA3_COMPUTE.GLOBAL[0xa].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +00044560 size 1, subchannel 2 (0x5c0000d2), offset 0x0560, increment +00000000 NVA3_COMPUTE.GLOBAL[0xb].ADDRESS_HIGH = 0 +00044564 size 1, subchannel 2 (0x5c0000d2), offset 0x0564, increment +00000000 NVA3_COMPUTE.GLOBAL[0xb].ADDRESS_LOW = 0 +0004456c size 1, subchannel 2 (0x5c0000d2), offset 0x056c, increment +00000000 NVA3_COMPUTE.GLOBAL[0xb].LIMIT = 0 +00044570 size 1, subchannel 2 (0x5c0000d2), offset 0x0570, increment +00000001 NVA3_COMPUTE.GLOBAL[0xb].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +00044580 size 1, subchannel 2 (0x5c0000d2), offset 0x0580, increment +00000000 NVA3_COMPUTE.GLOBAL[0xc].ADDRESS_HIGH = 0 +00044584 size 1, subchannel 2 (0x5c0000d2), offset 0x0584, increment +00000000 NVA3_COMPUTE.GLOBAL[0xc].ADDRESS_LOW = 0 +0004458c size 1, subchannel 2 (0x5c0000d2), offset 0x058c, increment +00000000 NVA3_COMPUTE.GLOBAL[0xc].LIMIT = 0 +00044590 size 1, subchannel 2 (0x5c0000d2), offset 0x0590, increment +00000001 NVA3_COMPUTE.GLOBAL[0xc].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +000445a0 size 1, subchannel 2 (0x5c0000d2), offset 0x05a0, increment +00000000 NVA3_COMPUTE.GLOBAL[0xd].ADDRESS_HIGH = 0 +000445a4 size 1, subchannel 2 (0x5c0000d2), offset 0x05a4, increment +00000000 NVA3_COMPUTE.GLOBAL[0xd].ADDRESS_LOW = 0 +000445ac size 1, subchannel 2 (0x5c0000d2), offset 0x05ac, increment +00000000 NVA3_COMPUTE.GLOBAL[0xd].LIMIT = 0 +000445b0 size 1, subchannel 2 (0x5c0000d2), offset 0x05b0, increment +00000001 NVA3_COMPUTE.GLOBAL[0xd].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +000445c0 size 1, subchannel 2 (0x5c0000d2), offset 0x05c0, increment +00000000 NVA3_COMPUTE.GLOBAL[0xe].ADDRESS_HIGH = 0 +000445c4 size 1, subchannel 2 (0x5c0000d2), offset 0x05c4, increment +00000000 NVA3_COMPUTE.GLOBAL[0xe].ADDRESS_LOW = 0 +000445cc size 1, subchannel 2 (0x5c0000d2), offset 0x05cc, increment +00000000 NVA3_COMPUTE.GLOBAL[0xe].LIMIT = 0 +000445d0 size 1, subchannel 2 (0x5c0000d2), offset 0x05d0, increment +00000001 NVA3_COMPUTE.GLOBAL[0xe].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +000445e0 size 1, subchannel 2 (0x5c0000d2), offset 0x05e0, increment +00000000 NVA3_COMPUTE.GLOBAL[0xf].ADDRESS_HIGH = 0 +000445e4 size 1, subchannel 2 (0x5c0000d2), offset 0x05e4, increment +00000000 NVA3_COMPUTE.GLOBAL[0xf].ADDRESS_LOW = 0 +000445ec size 1, subchannel 2 (0x5c0000d2), offset 0x05ec, increment +00000000 NVA3_COMPUTE.GLOBAL[0xf].LIMIT = 0 +000445f0 size 1, subchannel 2 (0x5c0000d2), offset 0x05f0, increment +00000001 NVA3_COMPUTE.GLOBAL[0xf].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +00044110 size 1, subchannel 2 (0x5c0000d2), offset 0x0110, increment +00000000 NVA3_COMPUTE.GRAPH.SERIALIZE = 0 +000445c0 size 1, subchannel 2 (0x5c0000d2), offset 0x05c0, increment +000000fe NVA3_COMPUTE.GLOBAL[0xe].ADDRESS_HIGH = 0xfe +000445c4 size 1, subchannel 2 (0x5c0000d2), offset 0x05c4, increment +fffe0000 NVA3_COMPUTE.GLOBAL[0xe].ADDRESS_LOW = 0xfffe0000 +000445cc size 1, subchannel 2 (0x5c0000d2), offset 0x05cc, increment +ffffffff NVA3_COMPUTE.GLOBAL[0xe].LIMIT = 0xffffffff +000445d0 size 1, subchannel 2 (0x5c0000d2), offset 0x05d0, increment +00000001 NVA3_COMPUTE.GLOBAL[0xe].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +000445e0 size 1, subchannel 2 (0x5c0000d2), offset 0x05e0, increment +00000000 NVA3_COMPUTE.GLOBAL[0xf].ADDRESS_HIGH = 0 +000445e4 size 1, subchannel 2 (0x5c0000d2), offset 0x05e4, increment +40300000 NVA3_COMPUTE.GLOBAL[0xf].ADDRESS_LOW = 0x40300000 +000445ec size 1, subchannel 2 (0x5c0000d2), offset 0x05ec, increment +403007ff NVA3_COMPUTE.GLOBAL[0xf].LIMIT = 0x403007ff +000445f0 size 1, subchannel 2 (0x5c0000d2), offset 0x05f0, increment +00000001 NVA3_COMPUTE.GLOBAL[0xf].MODE = { LINEAR | UNK1 = 0 | TILE_MODE = 0 } +000442fc size 1, subchannel 2 (0x5c0000d2), offset 0x02fc, increment +00000007 NVA3_COMPUTE.LOCAL_WARPS_LOG_ALLOC = 7 +00044300 size 1, subchannel 2 (0x5c0000d2), offset 0x0300, increment +00000001 NVA3_COMPUTE.LOCAL_WARPS_NO_CLAMP = TRUE +00044304 size 1, subchannel 2 (0x5c0000d2), offset 0x0304, increment +00000007 NVA3_COMPUTE.STACK_WARPS_LOG_ALLOC = 7 +00044308 size 1, subchannel 2 (0x5c0000d2), offset 0x0308, increment +00000001 NVA3_COMPUTE.STACK_WARPS_NO_CLAMP = TRUE +00044374 size 1, subchannel 2 (0x5c0000d2), offset 0x0374, increment +00000000 NVA3_COMPUTE.USER_PARAM_COUNT = { UNK0 = 0 | COUNT = 0 } +00046000 size 1, subchannel 3 (0x0), offset 0x0000, increment +5c0000d4 NV50_M2MF mapped to subchannel 3 +00046184 size 1, subchannel 3 (0x5c0000d4), offset 0x0184, increment +5c0000c5 NV50_M2MF.DMA_BUFFER_IN = 0x5c0000c5 +00046188 size 1, subchannel 3 (0x5c0000d4), offset 0x0188, increment +5c0000c5 NV50_M2MF.DMA_BUFFER_OUT = 0x5c0000c5 +00046180 size 1, subchannel 3 (0x5c0000d4), offset 0x0180, increment +5c0000c9 NV50_M2MF.DMA_NOTIFY = 0x5c0000c9 +00048000 size 1, subchannel 4 (0x0), offset 0x0000, increment +5c0000d3 NV50_2D mapped to subchannel 4 +00048188 size 1, subchannel 4 (0x5c0000d3), offset 0x0188, increment +5c0000c5 NV50_2D.DMA_SRC = 0x5c0000c5 +00048184 size 1, subchannel 4 (0x5c0000d3), offset 0x0184, increment +5c0000c5 NV50_2D.DMA_DST = 0x5c0000c5 +000441cc size 1, subchannel 2 (0x5c0000d2), offset 0x01cc, increment +5c0000c5 NVA3_COMPUTE.DMA_TEXTURE = 0x5c0000c5 +000443bc size 1, subchannel 2 (0x5c0000d2), offset 0x03bc, increment +00000074 NVA3_COMPUTE.TEX_LIMITS = { SAMPLERS_LOG2 = 4 | TEXTURES_LOG2 = 7 } +00044378 size 1, subchannel 2 (0x5c0000d2), offset 0x0378, increment +00000001 NVA3_COMPUTE.LINKED_TSC = TRUE +000441c8 size 1, subchannel 2 (0x5c0000d2), offset 0x01c8, increment +5c0000c5 NVA3_COMPUTE.DMA_TIC = 0x5c0000c5 +000442c4 size 1, subchannel 2 (0x5c0000d2), offset 0x02c4, increment +00000000 NVA3_COMPUTE.TIC_ADDRESS_HIGH = 0 +000442c8 size 1, subchannel 2 (0x5c0000d2), offset 0x02c8, increment +40300800 NVA3_COMPUTE.TIC_ADDRESS_LOW = 0x40300800 +000442cc size 1, subchannel 2 (0x5c0000d2), offset 0x02cc, increment +000003ff NVA3_COMPUTE.TIC_LIMIT = 1023 +000441c4 size 1, subchannel 2 (0x5c0000d2), offset 0x01c4, increment +5c0000c5 NVA3_COMPUTE.DMA_TSC = 0x5c0000c5 +0004422c size 1, subchannel 2 (0x5c0000d2), offset 0x022c, increment +00000000 NVA3_COMPUTE.TSC_ADDRESS_HIGH = 0 +00044230 size 1, subchannel 2 (0x5c0000d2), offset 0x0230, increment +40308800 NVA3_COMPUTE.TSC_ADDRESS_LOW = 0x40308800 +00044234 size 1, subchannel 2 (0x5c0000d2), offset 0x0234, increment +000003ff NVA3_COMPUTE.TSC_LIMIT = 1023 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000001 NVA3_COMPUTE.QUERY_SEQUENCE = 0x1 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# jump to 0x102000: 00000000 20102000 +0003b600 +# jump to 0x1023b4: 00000008 201023b4 +0004ae00 +# jump to 0x102860: 00000010 20102860 +00001e00 +# jump to 0x10287c: 00000018 2010287c +0002b600 +# jump to 0x102b30: 00000020 20102b30 +00001e00 +# jump to 0x102b4c: 00000028 20102b4c +0003d600 +# jump to 0x102f20: 00000030 20102f20 +00001e00 +# jump to 0x102f3c: 00000038 20102f3c +0002f600 +# jump to 0x103230: 00000040 20103230 +00001e00 +# jump to 0x10324c: 00000048 2010324c +00023e00 +# jump to 0x103488: 00000050 20103488 +00001e00 +# jump to 0x1034a4: 00000058 201034a4 +00011600 +# jump to 0x1035b8: 00000060 201035b8 +00001e00 +# jump to 0x1035d4: 00000068 201035d4 +00053600 +# jump to 0x103b08: 00000070 20103b08 +00001e00 +# jump to 0x103b24: 00000078 20103b24 +00022e00 +# jump to 0x103d50: 00000080 20103d50 +00001e00 +# jump to 0x103d6c: 00000088 20103d6c +00017600 +# jump to 0x103ee0: 00000090 20103ee0 +00001e00 +# jump to 0x103efc: 00000098 20103efc +00017600 +# jump to 0x104070: 000000a0 20104070 +00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000003 NV50_2D.SIFC_HEIGHT = 3 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000003 NV50_2D.DST_HEIGHT = 3 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1e00 NV50_2D.DST_ADDRESS_LOW = 0xfffc1e00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +43008860 size 192, subchannel 4 (0x5c0000d3), offset 0x0860, constant +a0004e15 NV50_2D.SIFC_DATA = 0xa0004e15 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +1000dc05 NV50_2D.SIFC_DATA = 0x1000dc05 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +40031409 NV50_2D.SIFC_DATA = 0x40031409 +00000780 NV50_2D.SIFC_DATA = 0x780 +30100409 NV50_2D.SIFC_DATA = 0x30100409 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60021405 NV50_2D.SIFC_DATA = 0x60021405 +00008780 NV50_2D.SIFC_DATA = 0x8780 +2000c805 NV50_2D.SIFC_DATA = 0x2000c805 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +d0800209 NV50_2D.SIFC_DATA = 0xd0800209 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +a0004c0d NV50_2D.SIFC_DATA = 0xa0004c0d +04200780 NV50_2D.SIFC_DATA = 0x4200780 +30048409 NV50_2D.SIFC_DATA = 0x30048409 +00000003 NV50_2D.SIFC_DATA = 0x3 +307cd219 NV50_2D.SIFC_DATA = 0x307cd219 +64208780 NV50_2D.SIFC_DATA = 0x64208780 +3080d021 NV50_2D.SIFC_DATA = 0x3080d021 +64610780 NV50_2D.SIFC_DATA = 0x64610780 +d0800411 NV50_2D.SIFC_DATA = 0xd0800411 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +a0000001 NV50_2D.SIFC_DATA = 0xa0000001 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +4006421d NV50_2D.SIFC_DATA = 0x4006421d +00200780 NV50_2D.SIFC_DATA = 0x200780 +d0080c19 NV50_2D.SIFC_DATA = 0xd0080c19 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +2040d025 NV50_2D.SIFC_DATA = 0x2040d025 +042107c0 NV50_2D.SIFC_DATA = 0x42107c0 +1000ee09 NV50_2D.SIFC_DATA = 0x1000ee09 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +20000e1d NV50_2D.SIFC_DATA = 0x20000e1d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +307cd221 NV50_2D.SIFC_DATA = 0x307cd221 +64210780 NV50_2D.SIFC_DATA = 0x64210780 +3140d229 NV50_2D.SIFC_DATA = 0x3140d229 +04604780 NV50_2D.SIFC_DATA = 0x4604780 +d0020009 NV50_2D.SIFC_DATA = 0xd0020009 +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +3000ec1d NV50_2D.SIFC_DATA = 0x3000ec1d +0421c7c0 NV50_2D.SIFC_DATA = 0x421c7c0 +30021225 NV50_2D.SIFC_DATA = 0x30021225 +e4100780 NV50_2D.SIFC_DATA = 0xe4100780 +301e1429 NV50_2D.SIFC_DATA = 0x301e1429 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +d0061019 NV50_2D.SIFC_DATA = 0xd0061019 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +3040f821 NV50_2D.SIFC_DATA = 0x3040f821 +04008780 NV50_2D.SIFC_DATA = 0x4008780 +d00a1209 NV50_2D.SIFC_DATA = 0xd00a1209 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +a000f9fd NV50_2D.SIFC_DATA = 0xa000f9fd +040047c8 NV50_2D.SIFC_DATA = 0x40047c8 +307c0e29 NV50_2D.SIFC_DATA = 0x307c0e29 +64018780 NV50_2D.SIFC_DATA = 0x64018780 +307c1025 NV50_2D.SIFC_DATA = 0x307c1025 +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +1000f809 NV50_2D.SIFC_DATA = 0x1000f809 +0403c280 NV50_2D.SIFC_DATA = 0x403c280 +d00a1229 NV50_2D.SIFC_DATA = 0xd00a1229 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +307c1025 NV50_2D.SIFC_DATA = 0x307c1025 +6c010780 NV50_2D.SIFC_DATA = 0x6c010780 +307c102d NV50_2D.SIFC_DATA = 0x307c102d +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +30020e09 NV50_2D.SIFC_DATA = 0x30020e09 +64004780 NV50_2D.SIFC_DATA = 0x64004780 +d00a1225 NV50_2D.SIFC_DATA = 0xd00a1225 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d002162d NV50_2D.SIFC_DATA = 0xd002162d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1000e009 NV50_2D.SIFC_DATA = 0x1000e009 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +307c1029 NV50_2D.SIFC_DATA = 0x307c1029 +6c004780 NV50_2D.SIFC_DATA = 0x6c004780 +400a0a21 NV50_2D.SIFC_DATA = 0x400a0a21 +00000780 NV50_2D.SIFC_DATA = 0x780 +d00b1429 NV50_2D.SIFC_DATA = 0xd00b1429 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +30101021 NV50_2D.SIFC_DATA = 0x30101021 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +d00a1225 NV50_2D.SIFC_DATA = 0xd00a1225 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +600a0809 NV50_2D.SIFC_DATA = 0x600a0809 +00020780 NV50_2D.SIFC_DATA = 0x20780 +d0090dfd NV50_2D.SIFC_DATA = 0xd0090dfd +040007c8 NV50_2D.SIFC_DATA = 0x40007c8 +2000cc19 NV50_2D.SIFC_DATA = 0x2000cc19 +04208780 NV50_2D.SIFC_DATA = 0x4208780 +10407003 NV50_2D.SIFC_DATA = 0x10407003 +00000100 NV50_2D.SIFC_DATA = 0x100 +307cd9fd NV50_2D.SIFC_DATA = 0x307cd9fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +307cdbfd NV50_2D.SIFC_DATA = 0x307cdbfd +642082c8 NV50_2D.SIFC_DATA = 0x642082c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000280 NV50_2D.SIFC_DATA = 0x280 +30020e15 NV50_2D.SIFC_DATA = 0x30020e15 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +1000f809 NV50_2D.SIFC_DATA = 0x1000f809 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +10000201 NV50_2D.SIFC_DATA = 0x10000201 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +2005881c NV50_2D.SIFC_DATA = 0x2005881c +20078c10 NV50_2D.SIFC_DATA = 0x20078c10 +d00e0811 NV50_2D.SIFC_DATA = 0xd00e0811 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +2000021d NV50_2D.SIFC_DATA = 0x2000021d +0401c780 NV50_2D.SIFC_DATA = 0x401c780 +21000409 NV50_2D.SIFC_DATA = 0x21000409 +044087c0 NV50_2D.SIFC_DATA = 0x44087c0 +3040060d NV50_2D.SIFC_DATA = 0x3040060d +041f0780 NV50_2D.SIFC_DATA = 0x41f0780 +3003dbfd NV50_2D.SIFC_DATA = 0x3003dbfd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +d0800021 NV50_2D.SIFC_DATA = 0xd0800021 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +d00e0e11 NV50_2D.SIFC_DATA = 0xd00e0e11 +a0c00780 NV50_2D.SIFC_DATA = 0xa0c00780 +3002d9fd NV50_2D.SIFC_DATA = 0x3002d9fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +2000e401 NV50_2D.SIFC_DATA = 0x2000e401 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +30049011 NV50_2D.SIFC_DATA = 0x30049011 +00000003 NV50_2D.SIFC_DATA = 0x3 +2000e405 NV50_2D.SIFC_DATA = 0x2000e405 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +3003dbfd NV50_2D.SIFC_DATA = 0x3003dbfd +64210148 NV50_2D.SIFC_DATA = 0x64210148 +2000e819 NV50_2D.SIFC_DATA = 0x2000e819 +04218780 NV50_2D.SIFC_DATA = 0x4218780 +d0800811 NV50_2D.SIFC_DATA = 0xd0800811 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +103f6003 NV50_2D.SIFC_DATA = 0x103f6003 +00000280 NV50_2D.SIFC_DATA = 0x280 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000780 NV50_2D.SIFC_DATA = 0x780 +307cd3fd NV50_2D.SIFC_DATA = 0x307cd3fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +a0004809 NV50_2D.SIFC_DATA = 0xa0004809 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +3000d1fd NV50_2D.SIFC_DATA = 0x3000d1fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +203f8409 NV50_2D.SIFC_DATA = 0x203f8409 +0fffffff NV50_2D.SIFC_DATA = 0xfffffff +307cd3fd NV50_2D.SIFC_DATA = 0x307cd3fd +64210148 NV50_2D.SIFC_DATA = 0x64210148 +300207fd NV50_2D.SIFC_DATA = 0x300207fd +640082c8 NV50_2D.SIFC_DATA = 0x640082c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +307cd9fd NV50_2D.SIFC_DATA = 0x307cd9fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +307cdbfd NV50_2D.SIFC_DATA = 0x307cdbfd +642082c8 NV50_2D.SIFC_DATA = 0x642082c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000280 NV50_2D.SIFC_DATA = 0x280 +1000f809 NV50_2D.SIFC_DATA = 0x1000f809 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +10000215 NV50_2D.SIFC_DATA = 0x10000215 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +300009fd NV50_2D.SIFC_DATA = 0x300009fd +6400c7c8 NV50_2D.SIFC_DATA = 0x6400c7c8 +20000011 NV50_2D.SIFC_DATA = 0x20000011 +04018500 NV50_2D.SIFC_DATA = 0x4018500 +d00e0811 NV50_2D.SIFC_DATA = 0xd00e0811 +80000500 NV50_2D.SIFC_DATA = 0x80000500 +2000001d NV50_2D.SIFC_DATA = 0x2000001d +04004500 NV50_2D.SIFC_DATA = 0x4004500 +d00e0e11 NV50_2D.SIFC_DATA = 0xd00e0e11 +a0000500 NV50_2D.SIFC_DATA = 0xa0000500 +2000d011 NV50_2D.SIFC_DATA = 0x2000d011 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +d0800811 NV50_2D.SIFC_DATA = 0xd0800811 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +300401fd NV50_2D.SIFC_DATA = 0x300401fd +640187c8 NV50_2D.SIFC_DATA = 0x640187c8 +a0424003 NV50_2D.SIFC_DATA = 0xa0424003 +00000000 NV50_2D.SIFC_DATA = 0 +10424003 NV50_2D.SIFC_DATA = 0x10424003 +00000280 NV50_2D.SIFC_DATA = 0x280 +2140f01c NV50_2D.SIFC_DATA = 0x2140f01c +20068e10 NV50_2D.SIFC_DATA = 0x20068e10 +203f8811 NV50_2D.SIFC_DATA = 0x203f8811 +0fffffff NV50_2D.SIFC_DATA = 0xfffffff +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000022 NV50_2D.SIFC_WIDTH = 34 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2100 NV50_2D.DST_ADDRESS_LOW = 0xfffc2100 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40888860 size 34, subchannel 4 (0x5c0000d3), offset 0x0860, constant +d00e0811 NV50_2D.SIFC_DATA = 0xd00e0811 +80000780 NV50_2D.SIFC_DATA = 0x80000780 +20000e1d NV50_2D.SIFC_DATA = 0x20000e1d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +203f8e1d NV50_2D.SIFC_DATA = 0x203f8e1d +0fffffff NV50_2D.SIFC_DATA = 0xfffffff +d00e0e11 NV50_2D.SIFC_DATA = 0xd00e0e11 +a0000780 NV50_2D.SIFC_DATA = 0xa0000780 +21000409 NV50_2D.SIFC_DATA = 0x21000409 +044087c2 NV50_2D.SIFC_DATA = 0x44087c2 +3040060d NV50_2D.SIFC_DATA = 0x3040060d +041f0780 NV50_2D.SIFC_DATA = 0x41f0780 +3003dbfd NV50_2D.SIFC_DATA = 0x3003dbfd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +d0800a11 NV50_2D.SIFC_DATA = 0xd0800a11 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +3002d9fd NV50_2D.SIFC_DATA = 0x3002d9fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +2000e819 NV50_2D.SIFC_DATA = 0x2000e819 +04218780 NV50_2D.SIFC_DATA = 0x4218780 +30048811 NV50_2D.SIFC_DATA = 0x30048811 +00000003 NV50_2D.SIFC_DATA = 0x3 +2000e405 NV50_2D.SIFC_DATA = 0x2000e405 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +3003dbfd NV50_2D.SIFC_DATA = 0x3003dbfd +64210148 NV50_2D.SIFC_DATA = 0x64210148 +2000e415 NV50_2D.SIFC_DATA = 0x2000e415 +04214780 NV50_2D.SIFC_DATA = 0x4214780 +d0800811 NV50_2D.SIFC_DATA = 0xd0800811 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +10414003 NV50_2D.SIFC_DATA = 0x10414003 +00000280 NV50_2D.SIFC_DATA = 0x280 +f0000001 NV50_2D.SIFC_DATA = 0xf0000001 +e0000001 NV50_2D.SIFC_DATA = 0xe0000001 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000002 NVA3_COMPUTE.QUERY_SEQUENCE = 0x2 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000003 NVA3_COMPUTE.QUERY_SEQUENCE = 0x3 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1c00 NV50_2D.DST_ADDRESS_LOW = 0xfffc1c00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +41008860 size 64, subchannel 4 (0x5c0000d3), offset 0x0860, constant +a0004e0d NV50_2D.SIFC_DATA = 0xa0004e0d +04200780 NV50_2D.SIFC_DATA = 0x4200780 +1000dc09 NV50_2D.SIFC_DATA = 0x1000dc09 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +1000e005 NV50_2D.SIFC_DATA = 0x1000e005 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +40050c14 NV50_2D.SIFC_DATA = 0x40050c14 +40060610 NV50_2D.SIFC_DATA = 0x40060610 +30100a15 NV50_2D.SIFC_DATA = 0x30100a15 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +30100811 NV50_2D.SIFC_DATA = 0x30100811 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +307cd9fd NV50_2D.SIFC_DATA = 0x307cd9fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +60040c09 NV50_2D.SIFC_DATA = 0x60040c09 +00014780 NV50_2D.SIFC_DATA = 0x14780 +60060405 NV50_2D.SIFC_DATA = 0x60060405 +00010780 NV50_2D.SIFC_DATA = 0x10780 +307cdbfd NV50_2D.SIFC_DATA = 0x307cdbfd +642082c8 NV50_2D.SIFC_DATA = 0x642082c8 +2102e808 NV50_2D.SIFC_DATA = 0x2102e808 +2101ec0c NV50_2D.SIFC_DATA = 0x2101ec0c +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000280 NV50_2D.SIFC_DATA = 0x280 +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000011 NV50_2D.SIFC_DATA = 0xa0000011 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1000ee01 NV50_2D.SIFC_DATA = 0x1000ee01 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +60024c05 NV50_2D.SIFC_DATA = 0x60024c05 +00210780 NV50_2D.SIFC_DATA = 0x210780 +d0000001 NV50_2D.SIFC_DATA = 0xd0000001 +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +3000ec05 NV50_2D.SIFC_DATA = 0x3000ec05 +042047c0 NV50_2D.SIFC_DATA = 0x42047c0 +3040f801 NV50_2D.SIFC_DATA = 0x3040f801 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +10208011 NV50_2D.SIFC_DATA = 0x10208011 +00000003 NV50_2D.SIFC_DATA = 0x3 +301e0215 NV50_2D.SIFC_DATA = 0x301e0215 +e4100780 NV50_2D.SIFC_DATA = 0xe4100780 +30020001 NV50_2D.SIFC_DATA = 0x30020001 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +210009fd NV50_2D.SIFC_DATA = 0x210009fd +044007c8 NV50_2D.SIFC_DATA = 0x44007c8 +d0050001 NV50_2D.SIFC_DATA = 0xd0050001 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +1000f801 NV50_2D.SIFC_DATA = 0x1000f801 +0403c980 NV50_2D.SIFC_DATA = 0x403c980 +30020211 NV50_2D.SIFC_DATA = 0x30020211 +c41007d0 NV50_2D.SIFC_DATA = 0xc41007d0 +3000d3fd NV50_2D.SIFC_DATA = 0x3000d3fd +6c2087c8 NV50_2D.SIFC_DATA = 0x6c2087c8 +3004d1fd NV50_2D.SIFC_DATA = 0x3004d1fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +3000d3fd NV50_2D.SIFC_DATA = 0x3000d3fd +6c210148 NV50_2D.SIFC_DATA = 0x6c210148 +1000f801 NV50_2D.SIFC_DATA = 0x1000f801 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1000f805 NV50_2D.SIFC_DATA = 0x1000f805 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +10000201 NV50_2D.SIFC_DATA = 0x10000201 +2440de00 NV50_2D.SIFC_DATA = 0x2440de00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000024 NV50_2D.SIFC_WIDTH = 36 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1d00 NV50_2D.DST_ADDRESS_LOW = 0xfffc1d00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40908860 size 36, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10000205 NV50_2D.SIFC_DATA = 0x10000205 +2440c280 NV50_2D.SIFC_DATA = 0x2440c280 +d0000215 NV50_2D.SIFC_DATA = 0xd0000215 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1000f801 NV50_2D.SIFC_DATA = 0x1000f801 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1000f805 NV50_2D.SIFC_DATA = 0x1000f805 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +307c0bfd NV50_2D.SIFC_DATA = 0x307c0bfd +6c0087c8 NV50_2D.SIFC_DATA = 0x6c0087c8 +20000819 NV50_2D.SIFC_DATA = 0x20000819 +0400c500 NV50_2D.SIFC_DATA = 0x400c500 +2000041d NV50_2D.SIFC_DATA = 0x2000041d +04010500 NV50_2D.SIFC_DATA = 0x4010500 +d00e0c19 NV50_2D.SIFC_DATA = 0xd00e0c19 +80c00500 NV50_2D.SIFC_DATA = 0x80c00500 +d00e0e19 NV50_2D.SIFC_DATA = 0xd00e0e19 +a0c00500 NV50_2D.SIFC_DATA = 0xa0c00500 +21000001 NV50_2D.SIFC_DATA = 0x21000001 +044047c0 NV50_2D.SIFC_DATA = 0x44047c0 +30400205 NV50_2D.SIFC_DATA = 0x30400205 +041f0780 NV50_2D.SIFC_DATA = 0x41f0780 +3001dbfd NV50_2D.SIFC_DATA = 0x3001dbfd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +3000d9fd NV50_2D.SIFC_DATA = 0x3000d9fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +3001dbfd NV50_2D.SIFC_DATA = 0x3001dbfd +64210148 NV50_2D.SIFC_DATA = 0x64210148 +2000e80d NV50_2D.SIFC_DATA = 0x2000e80d +0420c780 NV50_2D.SIFC_DATA = 0x420c780 +2000e409 NV50_2D.SIFC_DATA = 0x2000e409 +04208780 NV50_2D.SIFC_DATA = 0x4208780 +103a4003 NV50_2D.SIFC_DATA = 0x103a4003 +00000280 NV50_2D.SIFC_DATA = 0x280 +f0000001 NV50_2D.SIFC_DATA = 0xf0000001 +e0000001 NV50_2D.SIFC_DATA = 0xe0000001 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000004 NVA3_COMPUTE.QUERY_SEQUENCE = 0x4 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000005 NVA3_COMPUTE.QUERY_SEQUENCE = 0x5 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000002 NV50_2D.SIFC_HEIGHT = 2 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000002 NV50_2D.DST_HEIGHT = 2 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1900 NV50_2D.DST_ADDRESS_LOW = 0xfffc1900 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +42008860 size 128, subchannel 4 (0x5c0000d3), offset 0x0860, constant +a0004c29 NV50_2D.SIFC_DATA = 0xa0004c29 +042007d0 NV50_2D.SIFC_DATA = 0x42007d0 +a0004e05 NV50_2D.SIFC_DATA = 0xa0004e05 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +307c15fd NV50_2D.SIFC_DATA = 0x307c15fd +640087c8 NV50_2D.SIFC_DATA = 0x640087c8 +10337003 NV50_2D.SIFC_DATA = 0x10337003 +00001680 NV50_2D.SIFC_DATA = 0x1680 +307c03fd NV50_2D.SIFC_DATA = 0x307c03fd +640147d8 NV50_2D.SIFC_DATA = 0x640147d8 +1000f815 NV50_2D.SIFC_DATA = 0x1000f815 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1000d421 NV50_2D.SIFC_DATA = 0x1000d421 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +301fd425 NV50_2D.SIFC_DATA = 0x301fd425 +ec300780 NV50_2D.SIFC_DATA = 0xec300780 +a0000011 NV50_2D.SIFC_DATA = 0xa0000011 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1033d003 NV50_2D.SIFC_DATA = 0x1033d003 +00001280 NV50_2D.SIFC_DATA = 0x1280 +300513fd NV50_2D.SIFC_DATA = 0x300513fd +640087d8 NV50_2D.SIFC_DATA = 0x640087d8 +300411fd NV50_2D.SIFC_DATA = 0x300411fd +6400d2d8 NV50_2D.SIFC_DATA = 0x6400d2d8 +300513fd NV50_2D.SIFC_DATA = 0x300513fd +64005158 NV50_2D.SIFC_DATA = 0x64005158 +a033c003 NV50_2D.SIFC_DATA = 0xa033c003 +00000000 NV50_2D.SIFC_DATA = 0 +1033c003 NV50_2D.SIFC_DATA = 0x1033c003 +00001280 NV50_2D.SIFC_DATA = 0x1280 +d0800211 NV50_2D.SIFC_DATA = 0xd0800211 +00400780 NV50_2D.SIFC_DATA = 0x400780 +a00009fd NV50_2D.SIFC_DATA = 0xa00009fd +040007d8 NV50_2D.SIFC_DATA = 0x40007d8 +1033c003 NV50_2D.SIFC_DATA = 0x1033c003 +00001280 NV50_2D.SIFC_DATA = 0x1280 +2000cc09 NV50_2D.SIFC_DATA = 0x2000cc09 +04210780 NV50_2D.SIFC_DATA = 0x4210780 +d00e0409 NV50_2D.SIFC_DATA = 0xd00e0409 +80000780 NV50_2D.SIFC_DATA = 0x80000780 +2000c80d NV50_2D.SIFC_DATA = 0x2000c80d +04210780 NV50_2D.SIFC_DATA = 0x4210780 +d00e0609 NV50_2D.SIFC_DATA = 0xd00e0609 +a0000780 NV50_2D.SIFC_DATA = 0xa0000780 +1033c003 NV50_2D.SIFC_DATA = 0x1033c003 +00000780 NV50_2D.SIFC_DATA = 0x780 +1000f815 NV50_2D.SIFC_DATA = 0x1000f815 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1000d421 NV50_2D.SIFC_DATA = 0x1000d421 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +301fd425 NV50_2D.SIFC_DATA = 0x301fd425 +ec300780 NV50_2D.SIFC_DATA = 0xec300780 +a0000011 NV50_2D.SIFC_DATA = 0xa0000011 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1033d003 NV50_2D.SIFC_DATA = 0x1033d003 +00000780 NV50_2D.SIFC_DATA = 0x780 +f0000001 NV50_2D.SIFC_DATA = 0xf0000001 +e0000002 NV50_2D.SIFC_DATA = 0xe0000002 +10353003 NV50_2D.SIFC_DATA = 0x10353003 +00000100 NV50_2D.SIFC_DATA = 0x100 +d0090009 NV50_2D.SIFC_DATA = 0xd0090009 +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +2040d019 NV50_2D.SIFC_DATA = 0x2040d019 +042207c0 NV50_2D.SIFC_DATA = 0x42207c0 +307c03fd NV50_2D.SIFC_DATA = 0x307c03fd +640147d8 NV50_2D.SIFC_DATA = 0x640147d8 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +3040d21d NV50_2D.SIFC_DATA = 0x3040d21d +04208780 NV50_2D.SIFC_DATA = 0x4208780 +d0810c09 NV50_2D.SIFC_DATA = 0xd0810c09 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +1035a003 NV50_2D.SIFC_DATA = 0x1035a003 +00001280 NV50_2D.SIFC_DATA = 0x1280 +300507fd NV50_2D.SIFC_DATA = 0x300507fd +640087c8 NV50_2D.SIFC_DATA = 0x640087c8 +300405fd NV50_2D.SIFC_DATA = 0x300405fd +6400c2c8 NV50_2D.SIFC_DATA = 0x6400c2c8 +300507fd NV50_2D.SIFC_DATA = 0x300507fd +64004148 NV50_2D.SIFC_DATA = 0x64004148 +a0359003 NV50_2D.SIFC_DATA = 0xa0359003 +00000000 NV50_2D.SIFC_DATA = 0 +10359003 NV50_2D.SIFC_DATA = 0x10359003 +00000280 NV50_2D.SIFC_DATA = 0x280 +d0800201 NV50_2D.SIFC_DATA = 0xd0800201 +00400780 NV50_2D.SIFC_DATA = 0x400780 +a00001fd NV50_2D.SIFC_DATA = 0xa00001fd +040007c8 NV50_2D.SIFC_DATA = 0x40007c8 +10359003 NV50_2D.SIFC_DATA = 0x10359003 +00000280 NV50_2D.SIFC_DATA = 0x280 +2142f000 NV50_2D.SIFC_DATA = 0x2142f000 +20008824 NV50_2D.SIFC_DATA = 0x20008824 +2000cc01 NV50_2D.SIFC_DATA = 0x2000cc01 +04224780 NV50_2D.SIFC_DATA = 0x4224780 +d00e0001 NV50_2D.SIFC_DATA = 0xd00e0001 +80000780 NV50_2D.SIFC_DATA = 0x80000780 +2000c825 NV50_2D.SIFC_DATA = 0x2000c825 +04224780 NV50_2D.SIFC_DATA = 0x4224780 +d00e1201 NV50_2D.SIFC_DATA = 0xd00e1201 +a0000780 NV50_2D.SIFC_DATA = 0xa0000780 +10359003 NV50_2D.SIFC_DATA = 0x10359003 +00000780 NV50_2D.SIFC_DATA = 0x780 +d0090001 NV50_2D.SIFC_DATA = 0xd0090001 +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +2040d019 NV50_2D.SIFC_DATA = 0x2040d019 +042207c0 NV50_2D.SIFC_DATA = 0x42207c0 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +3040d21d NV50_2D.SIFC_DATA = 0x3040d21d +04200780 NV50_2D.SIFC_DATA = 0x4200780 +d0810c09 NV50_2D.SIFC_DATA = 0xd0810c09 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +1035a003 NV50_2D.SIFC_DATA = 0x1035a003 +00000780 NV50_2D.SIFC_DATA = 0x780 +f0000001 NV50_2D.SIFC_DATA = 0xf0000001 +e0000002 NV50_2D.SIFC_DATA = 0xe0000002 +40034801 NV50_2D.SIFC_DATA = 0x40034801 +00200780 NV50_2D.SIFC_DATA = 0x200780 +30100001 NV50_2D.SIFC_DATA = 0x30100001 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60024801 NV50_2D.SIFC_DATA = 0x60024801 +00200780 NV50_2D.SIFC_DATA = 0x200780 +20000001 NV50_2D.SIFC_DATA = 0x20000001 +04028780 NV50_2D.SIFC_DATA = 0x4028780 +40014205 NV50_2D.SIFC_DATA = 0x40014205 +00200780 NV50_2D.SIFC_DATA = 0x200780 +30100205 NV50_2D.SIFC_DATA = 0x30100205 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +0000002c NV50_2D.SIFC_WIDTH = 44 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1b00 NV50_2D.DST_ADDRESS_LOW = 0xfffc1b00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40b08860 size 44, subchannel 4 (0x5c0000d3), offset 0x0860, constant +60004201 NV50_2D.SIFC_DATA = 0x60004201 +00204780 NV50_2D.SIFC_DATA = 0x204780 +20000001 NV50_2D.SIFC_DATA = 0x20000001 +040107c0 NV50_2D.SIFC_DATA = 0x40107c0 +3040f815 NV50_2D.SIFC_DATA = 0x3040f815 +04014780 NV50_2D.SIFC_DATA = 0x4014780 +10208011 NV50_2D.SIFC_DATA = 0x10208011 +00000003 NV50_2D.SIFC_DATA = 0x3 +301e0005 NV50_2D.SIFC_DATA = 0x301e0005 +e4100780 NV50_2D.SIFC_DATA = 0xe4100780 +30020a15 NV50_2D.SIFC_DATA = 0x30020a15 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +20400c09 NV50_2D.SIFC_DATA = 0x20400c09 +040087d0 NV50_2D.SIFC_DATA = 0x40087d0 +210009fd NV50_2D.SIFC_DATA = 0x210009fd +044087c8 NV50_2D.SIFC_DATA = 0x44087c8 +d003000d NV50_2D.SIFC_DATA = 0xd003000d +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +d0010a05 NV50_2D.SIFC_DATA = 0xd0010a05 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +30400e0d NV50_2D.SIFC_DATA = 0x30400e0d +0400d780 NV50_2D.SIFC_DATA = 0x400d780 +1000f805 NV50_2D.SIFC_DATA = 0x1000f805 +0403c980 NV50_2D.SIFC_DATA = 0x403c980 +30020001 NV50_2D.SIFC_DATA = 0x30020001 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +300303fd NV50_2D.SIFC_DATA = 0x300303fd +640087c8 NV50_2D.SIFC_DATA = 0x640087c8 +300201fd NV50_2D.SIFC_DATA = 0x300201fd +640182c8 NV50_2D.SIFC_DATA = 0x640182c8 +300303fd NV50_2D.SIFC_DATA = 0x300303fd +64010148 NV50_2D.SIFC_DATA = 0x64010148 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000280 NV50_2D.SIFC_DATA = 0x280 +2108ec04 NV50_2D.SIFC_DATA = 0x2108ec04 +2108e808 NV50_2D.SIFC_DATA = 0x2108e808 +20000005 NV50_2D.SIFC_DATA = 0x20000005 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d00e0205 NV50_2D.SIFC_DATA = 0xd00e0205 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +20000001 NV50_2D.SIFC_DATA = 0x20000001 +04008780 NV50_2D.SIFC_DATA = 0x4008780 +d00e0005 NV50_2D.SIFC_DATA = 0xd00e0005 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000006 NVA3_COMPUTE.QUERY_SEQUENCE = 0x6 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000007 NVA3_COMPUTE.QUERY_SEQUENCE = 0x7 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1700 NV50_2D.DST_ADDRESS_LOW = 0xfffc1700 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +41008860 size 64, subchannel 4 (0x5c0000d3), offset 0x0860, constant +a0004c0d NV50_2D.SIFC_DATA = 0xa0004c0d +042007d0 NV50_2D.SIFC_DATA = 0x42007d0 +a0004e09 NV50_2D.SIFC_DATA = 0xa0004e09 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +307c07fd NV50_2D.SIFC_DATA = 0x307c07fd +640087c8 NV50_2D.SIFC_DATA = 0x640087c8 +102f2003 NV50_2D.SIFC_DATA = 0x102f2003 +00001680 NV50_2D.SIFC_DATA = 0x1680 +307c05fd NV50_2D.SIFC_DATA = 0x307c05fd +640147d8 NV50_2D.SIFC_DATA = 0x640147d8 +a0000011 NV50_2D.SIFC_DATA = 0xa0000011 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +102f5003 NV50_2D.SIFC_DATA = 0x102f5003 +00001280 NV50_2D.SIFC_DATA = 0x1280 +3004d3fd NV50_2D.SIFC_DATA = 0x3004d3fd +6420c7d8 NV50_2D.SIFC_DATA = 0x6420c7d8 +a02f4003 NV50_2D.SIFC_DATA = 0xa02f4003 +00000000 NV50_2D.SIFC_DATA = 0 +102f4003 NV50_2D.SIFC_DATA = 0x102f4003 +00001280 NV50_2D.SIFC_DATA = 0x1280 +d0800209 NV50_2D.SIFC_DATA = 0xd0800209 +00400780 NV50_2D.SIFC_DATA = 0x400780 +a00005fd NV50_2D.SIFC_DATA = 0xa00005fd +040007d8 NV50_2D.SIFC_DATA = 0x40007d8 +102f4003 NV50_2D.SIFC_DATA = 0x102f4003 +00001280 NV50_2D.SIFC_DATA = 0x1280 +2000cc05 NV50_2D.SIFC_DATA = 0x2000cc05 +04210780 NV50_2D.SIFC_DATA = 0x4210780 +d00e0205 NV50_2D.SIFC_DATA = 0xd00e0205 +80000780 NV50_2D.SIFC_DATA = 0x80000780 +2000c815 NV50_2D.SIFC_DATA = 0x2000c815 +04210780 NV50_2D.SIFC_DATA = 0x4210780 +d00e0a05 NV50_2D.SIFC_DATA = 0xd00e0a05 +a0000780 NV50_2D.SIFC_DATA = 0xa0000780 +102f4003 NV50_2D.SIFC_DATA = 0x102f4003 +00000780 NV50_2D.SIFC_DATA = 0x780 +a0000011 NV50_2D.SIFC_DATA = 0xa0000011 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +102f5003 NV50_2D.SIFC_DATA = 0x102f5003 +00000780 NV50_2D.SIFC_DATA = 0x780 +f0000001 NV50_2D.SIFC_DATA = 0xf0000001 +e0000002 NV50_2D.SIFC_DATA = 0xe0000002 +10306003 NV50_2D.SIFC_DATA = 0x10306003 +00000100 NV50_2D.SIFC_DATA = 0x100 +1100f204 NV50_2D.SIFC_DATA = 0x1100f204 +2141f004 NV50_2D.SIFC_DATA = 0x2141f004 +307c05fd NV50_2D.SIFC_DATA = 0x307c05fd +640147c8 NV50_2D.SIFC_DATA = 0x640147c8 +d0810215 NV50_2D.SIFC_DATA = 0xd0810215 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +1030a003 NV50_2D.SIFC_DATA = 0x1030a003 +00000280 NV50_2D.SIFC_DATA = 0x280 +30040bfd NV50_2D.SIFC_DATA = 0x30040bfd +6400c7c8 NV50_2D.SIFC_DATA = 0x6400c7c8 +a0309003 NV50_2D.SIFC_DATA = 0xa0309003 +00000000 NV50_2D.SIFC_DATA = 0 +10309003 NV50_2D.SIFC_DATA = 0x10309003 +00000280 NV50_2D.SIFC_DATA = 0x280 +d0800201 NV50_2D.SIFC_DATA = 0xd0800201 +00400780 NV50_2D.SIFC_DATA = 0x400780 +a00001fd NV50_2D.SIFC_DATA = 0xa00001fd +040007c8 NV50_2D.SIFC_DATA = 0x40007c8 +10309003 NV50_2D.SIFC_DATA = 0x10309003 +00000280 NV50_2D.SIFC_DATA = 0x280 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000034 NV50_2D.SIFC_WIDTH = 52 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1800 NV50_2D.DST_ADDRESS_LOW = 0xfffc1800 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40d08860 size 52, subchannel 4 (0x5c0000d3), offset 0x0860, constant +2145f000 NV50_2D.SIFC_DATA = 0x2145f000 +20048018 NV50_2D.SIFC_DATA = 0x20048018 +2000cc01 NV50_2D.SIFC_DATA = 0x2000cc01 +04218780 NV50_2D.SIFC_DATA = 0x4218780 +d00e0001 NV50_2D.SIFC_DATA = 0xd00e0001 +80000780 NV50_2D.SIFC_DATA = 0x80000780 +2000c819 NV50_2D.SIFC_DATA = 0x2000c819 +04218780 NV50_2D.SIFC_DATA = 0x4218780 +d00e0c01 NV50_2D.SIFC_DATA = 0xd00e0c01 +a0000780 NV50_2D.SIFC_DATA = 0xa0000780 +10309003 NV50_2D.SIFC_DATA = 0x10309003 +00000780 NV50_2D.SIFC_DATA = 0x780 +1100f200 NV50_2D.SIFC_DATA = 0x1100f200 +2140f004 NV50_2D.SIFC_DATA = 0x2140f004 +d0810215 NV50_2D.SIFC_DATA = 0xd0810215 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +1030a003 NV50_2D.SIFC_DATA = 0x1030a003 +00000780 NV50_2D.SIFC_DATA = 0x780 +f0000001 NV50_2D.SIFC_DATA = 0xf0000001 +e0000002 NV50_2D.SIFC_DATA = 0xe0000002 +40054801 NV50_2D.SIFC_DATA = 0x40054801 +00200780 NV50_2D.SIFC_DATA = 0x200780 +30100001 NV50_2D.SIFC_DATA = 0x30100001 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60044801 NV50_2D.SIFC_DATA = 0x60044801 +00200780 NV50_2D.SIFC_DATA = 0x200780 +20000001 NV50_2D.SIFC_DATA = 0x20000001 +0400c780 NV50_2D.SIFC_DATA = 0x400c780 +40014209 NV50_2D.SIFC_DATA = 0x40014209 +00200780 NV50_2D.SIFC_DATA = 0x200780 +30100409 NV50_2D.SIFC_DATA = 0x30100409 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60004201 NV50_2D.SIFC_DATA = 0x60004201 +00208780 NV50_2D.SIFC_DATA = 0x208780 +20048000 NV50_2D.SIFC_DATA = 0x20048000 +20458208 NV50_2D.SIFC_DATA = 0x20458208 +30020005 NV50_2D.SIFC_DATA = 0x30020005 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +300203fd NV50_2D.SIFC_DATA = 0x300203fd +640187c8 NV50_2D.SIFC_DATA = 0x640187c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000280 NV50_2D.SIFC_DATA = 0x280 +1100f200 NV50_2D.SIFC_DATA = 0x1100f200 +2100ec08 NV50_2D.SIFC_DATA = 0x2100ec08 +2100e800 NV50_2D.SIFC_DATA = 0x2100e800 +20028208 NV50_2D.SIFC_DATA = 0x20028208 +20000205 NV50_2D.SIFC_DATA = 0x20000205 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d00e0401 NV50_2D.SIFC_DATA = 0xd00e0401 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000008 NVA3_COMPUTE.QUERY_SEQUENCE = 0x8 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000009 NVA3_COMPUTE.QUERY_SEQUENCE = 0x9 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1500 NV50_2D.DST_ADDRESS_LOW = 0xfffc1500 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +41008860 size 64, subchannel 4 (0x5c0000d3), offset 0x0860, constant +a0004c09 NV50_2D.SIFC_DATA = 0xa0004c09 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +10004e09 NV50_2D.SIFC_DATA = 0x10004e09 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +60024805 NV50_2D.SIFC_DATA = 0x60024805 +00208780 NV50_2D.SIFC_DATA = 0x208780 +40034209 NV50_2D.SIFC_DATA = 0x40034209 +00200780 NV50_2D.SIFC_DATA = 0x200780 +30100409 NV50_2D.SIFC_DATA = 0x30100409 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60024205 NV50_2D.SIFC_DATA = 0x60024205 +00208780 NV50_2D.SIFC_DATA = 0x208780 +301fd409 NV50_2D.SIFC_DATA = 0x301fd409 +ec300780 NV50_2D.SIFC_DATA = 0xec300780 +a0000001 NV50_2D.SIFC_DATA = 0xa0000001 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +3000d405 NV50_2D.SIFC_DATA = 0x3000d405 +042047c0 NV50_2D.SIFC_DATA = 0x42047c0 +d0020009 NV50_2D.SIFC_DATA = 0xd0020009 +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +20000001 NV50_2D.SIFC_DATA = 0x20000001 +040047d0 NV50_2D.SIFC_DATA = 0x40047d0 +3040f805 NV50_2D.SIFC_DATA = 0x3040f805 +04008780 NV50_2D.SIFC_DATA = 0x4008780 +3040f809 NV50_2D.SIFC_DATA = 0x3040f809 +04005780 NV50_2D.SIFC_DATA = 0x4005780 +10208005 NV50_2D.SIFC_DATA = 0x10208005 +00000003 NV50_2D.SIFC_DATA = 0x3 +301e000d NV50_2D.SIFC_DATA = 0x301e000d +e4100780 NV50_2D.SIFC_DATA = 0xe4100780 +30020409 NV50_2D.SIFC_DATA = 0x30020409 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +210003fd NV50_2D.SIFC_DATA = 0x210003fd +044007c8 NV50_2D.SIFC_DATA = 0x44007c8 +d0030405 NV50_2D.SIFC_DATA = 0xd0030405 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +30020001 NV50_2D.SIFC_DATA = 0x30020001 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +1000f805 NV50_2D.SIFC_DATA = 0x1000f805 +0403c980 NV50_2D.SIFC_DATA = 0x403c980 +307c000d NV50_2D.SIFC_DATA = 0x307c000d +64018780 NV50_2D.SIFC_DATA = 0x64018780 +3000d015 NV50_2D.SIFC_DATA = 0x3000d015 +64210780 NV50_2D.SIFC_DATA = 0x64210780 +307c0209 NV50_2D.SIFC_DATA = 0x307c0209 +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +3001d211 NV50_2D.SIFC_DATA = 0x3001d211 +6c208780 NV50_2D.SIFC_DATA = 0x6c208780 +d003040d NV50_2D.SIFC_DATA = 0xd003040d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0050815 NV50_2D.SIFC_DATA = 0xd0050815 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +307c0209 NV50_2D.SIFC_DATA = 0x307c0209 +6c010780 NV50_2D.SIFC_DATA = 0x6c010780 +3001d211 NV50_2D.SIFC_DATA = 0x3001d211 +6c210780 NV50_2D.SIFC_DATA = 0x6c210780 +d0030405 NV50_2D.SIFC_DATA = 0xd0030405 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d0050809 NV50_2D.SIFC_DATA = 0xd0050809 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d00203fd NV50_2D.SIFC_DATA = 0xd00203fd +040007c8 NV50_2D.SIFC_DATA = 0x40007c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000006 NV50_2D.SIFC_WIDTH = 6 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1600 NV50_2D.DST_ADDRESS_LOW = 0xfffc1600 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40188860 size 6, subchannel 4 (0x5c0000d3), offset 0x0860, constant +2100ec08 NV50_2D.SIFC_DATA = 0x2100ec08 +2100e804 NV50_2D.SIFC_DATA = 0x2100e804 +d00e0401 NV50_2D.SIFC_DATA = 0xd00e0401 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000000a NVA3_COMPUTE.QUERY_SEQUENCE = 0xa +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000000b NVA3_COMPUTE.QUERY_SEQUENCE = 0xb +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +0000001e NV50_2D.SIFC_WIDTH = 30 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1400 NV50_2D.DST_ADDRESS_LOW = 0xfffc1400 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40788860 size 30, subchannel 4 (0x5c0000d3), offset 0x0860, constant +a0004c09 NV50_2D.SIFC_DATA = 0xa0004c09 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +10004e09 NV50_2D.SIFC_DATA = 0x10004e09 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +60024805 NV50_2D.SIFC_DATA = 0x60024805 +00208780 NV50_2D.SIFC_DATA = 0x208780 +40034209 NV50_2D.SIFC_DATA = 0x40034209 +00200780 NV50_2D.SIFC_DATA = 0x200780 +30100409 NV50_2D.SIFC_DATA = 0x30100409 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60024205 NV50_2D.SIFC_DATA = 0x60024205 +00208780 NV50_2D.SIFC_DATA = 0x208780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +3101f200 NV50_2D.SIFC_DATA = 0x3101f200 +20028000 NV50_2D.SIFC_DATA = 0x20028000 +30020001 NV50_2D.SIFC_DATA = 0x30020001 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +307c01fd NV50_2D.SIFC_DATA = 0x307c01fd +6c0187c8 NV50_2D.SIFC_DATA = 0x6c0187c8 +3000d1fd NV50_2D.SIFC_DATA = 0x3000d1fd +6c2102c8 NV50_2D.SIFC_DATA = 0x6c2102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +2100ec08 NV50_2D.SIFC_DATA = 0x2100ec08 +2100e804 NV50_2D.SIFC_DATA = 0x2100e804 +d00e0401 NV50_2D.SIFC_DATA = 0xd00e0401 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000000c NVA3_COMPUTE.QUERY_SEQUENCE = 0xc +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000000d NVA3_COMPUTE.QUERY_SEQUENCE = 0xd +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000004 NV50_2D.SIFC_HEIGHT = 4 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000004 NV50_2D.DST_HEIGHT = 4 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0f00 NV50_2D.DST_ADDRESS_LOW = 0xfffc0f00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +44008860 size 256, subchannel 4 (0x5c0000d3), offset 0x0860, constant +a0004e09 NV50_2D.SIFC_DATA = 0xa0004e09 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +1000d805 NV50_2D.SIFC_DATA = 0x1000d805 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +4004060d NV50_2D.SIFC_DATA = 0x4004060d +00000780 NV50_2D.SIFC_DATA = 0x780 +3010060d NV50_2D.SIFC_DATA = 0x3010060d +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60040405 NV50_2D.SIFC_DATA = 0x60040405 +0000c780 NV50_2D.SIFC_DATA = 0xc780 +2000c811 NV50_2D.SIFC_DATA = 0x2000c811 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +d0800805 NV50_2D.SIFC_DATA = 0xd0800805 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +30048205 NV50_2D.SIFC_DATA = 0x30048205 +00000003 NV50_2D.SIFC_DATA = 0x3 +a0004c15 NV50_2D.SIFC_DATA = 0xa0004c15 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +d080020d NV50_2D.SIFC_DATA = 0xd080020d +04400780 NV50_2D.SIFC_DATA = 0x4400780 +1000e205 NV50_2D.SIFC_DATA = 0x1000e205 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +a0000021 NV50_2D.SIFC_DATA = 0xa0000021 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +2040d029 NV50_2D.SIFC_DATA = 0x2040d029 +0420c7c0 NV50_2D.SIFC_DATA = 0x420c7c0 +400a421d NV50_2D.SIFC_DATA = 0x400a421d +00200780 NV50_2D.SIFC_DATA = 0x200780 +307cd219 NV50_2D.SIFC_DATA = 0x307cd219 +64208780 NV50_2D.SIFC_DATA = 0x64208780 +3080d00d NV50_2D.SIFC_DATA = 0x3080d00d +64610780 NV50_2D.SIFC_DATA = 0x64610780 +3140d201 NV50_2D.SIFC_DATA = 0x3140d201 +04604780 NV50_2D.SIFC_DATA = 0x4604780 +20000e25 NV50_2D.SIFC_DATA = 0x20000e25 +04020780 NV50_2D.SIFC_DATA = 0x4020780 +d001001d NV50_2D.SIFC_DATA = 0xd001001d +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +30021405 NV50_2D.SIFC_DATA = 0x30021405 +e4100780 NV50_2D.SIFC_DATA = 0xe4100780 +301e0029 NV50_2D.SIFC_DATA = 0x301e0029 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +3000e025 NV50_2D.SIFC_DATA = 0x3000e025 +042247c0 NV50_2D.SIFC_DATA = 0x42247c0 +d0030c19 NV50_2D.SIFC_DATA = 0xd0030c19 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d00a0205 NV50_2D.SIFC_DATA = 0xd00a0205 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +3040f80d NV50_2D.SIFC_DATA = 0x3040f80d +0401c780 NV50_2D.SIFC_DATA = 0x401c780 +307cd21d NV50_2D.SIFC_DATA = 0x307cd21d +64210780 NV50_2D.SIFC_DATA = 0x64210780 +a000f9fd NV50_2D.SIFC_DATA = 0xa000f9fd +040047c8 NV50_2D.SIFC_DATA = 0x40047c8 +307c1231 NV50_2D.SIFC_DATA = 0x307c1231 +64018780 NV50_2D.SIFC_DATA = 0x64018780 +307c0629 NV50_2D.SIFC_DATA = 0x307c0629 +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +d0060e19 NV50_2D.SIFC_DATA = 0xd0060e19 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +3002002d NV50_2D.SIFC_DATA = 0x3002002d +e4100780 NV50_2D.SIFC_DATA = 0xe4100780 +1000f805 NV50_2D.SIFC_DATA = 0x1000f805 +0403c280 NV50_2D.SIFC_DATA = 0x403c280 +d00c141d NV50_2D.SIFC_DATA = 0xd00c141d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1000dc01 NV50_2D.SIFC_DATA = 0x1000dc01 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +300b0629 NV50_2D.SIFC_DATA = 0x300b0629 +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +30011231 NV50_2D.SIFC_DATA = 0x30011231 +64004780 NV50_2D.SIFC_DATA = 0x64004780 +300b0605 NV50_2D.SIFC_DATA = 0x300b0605 +6c004780 NV50_2D.SIFC_DATA = 0x6c004780 +307c060d NV50_2D.SIFC_DATA = 0x307c060d +6c010780 NV50_2D.SIFC_DATA = 0x6c010780 +d00c1429 NV50_2D.SIFC_DATA = 0xd00c1429 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d007061d NV50_2D.SIFC_DATA = 0xd007061d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +4001080d NV50_2D.SIFC_DATA = 0x4001080d +00000780 NV50_2D.SIFC_DATA = 0x780 +d00a0229 NV50_2D.SIFC_DATA = 0xd00a0229 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +30100605 NV50_2D.SIFC_DATA = 0x30100605 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +d00a0e0d NV50_2D.SIFC_DATA = 0xd00a0e0d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +6000081d NV50_2D.SIFC_DATA = 0x6000081d +00004780 NV50_2D.SIFC_DATA = 0x4780 +d0030dfd NV50_2D.SIFC_DATA = 0xd0030dfd +040007c8 NV50_2D.SIFC_DATA = 0x40007c8 +1000f805 NV50_2D.SIFC_DATA = 0x1000f805 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +10008400 NV50_2D.SIFC_DATA = 0x10008400 +2107ec1c NV50_2D.SIFC_DATA = 0x2107ec1c +10000819 NV50_2D.SIFC_DATA = 0x10000819 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +10231003 NV50_2D.SIFC_DATA = 0x10231003 +00000100 NV50_2D.SIFC_DATA = 0x100 +3003d7fd NV50_2D.SIFC_DATA = 0x3003d7fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +3002d5fd NV50_2D.SIFC_DATA = 0x3002d5fd +6420c2c8 NV50_2D.SIFC_DATA = 0x6420c2c8 +3003d7fd NV50_2D.SIFC_DATA = 0x3003d7fd +64204148 NV50_2D.SIFC_DATA = 0x64204148 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000280 NV50_2D.SIFC_DATA = 0x280 +1000dc15 NV50_2D.SIFC_DATA = 0x1000dc15 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +a0004a09 NV50_2D.SIFC_DATA = 0xa0004a09 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +1000d80d NV50_2D.SIFC_DATA = 0x1000d80d +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +400b0828 NV50_2D.SIFC_DATA = 0x400b0828 +40040e20 NV50_2D.SIFC_DATA = 0x40040e20 +3010142d NV50_2D.SIFC_DATA = 0x3010142d +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +30101029 NV50_2D.SIFC_DATA = 0x30101029 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +600a0821 NV50_2D.SIFC_DATA = 0x600a0821 +0002c780 NV50_2D.SIFC_DATA = 0x2c780 +60040c15 NV50_2D.SIFC_DATA = 0x60040c15 +00028780 NV50_2D.SIFC_DATA = 0x28780 +30021225 NV50_2D.SIFC_DATA = 0x30021225 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +d0800829 NV50_2D.SIFC_DATA = 0xd0800829 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +30049429 NV50_2D.SIFC_DATA = 0x30049429 +00000003 NV50_2D.SIFC_DATA = 0x3 +d0801429 NV50_2D.SIFC_DATA = 0xd0801429 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +2009942c NV50_2D.SIFC_DATA = 0x2009942c +200b8e28 NV50_2D.SIFC_DATA = 0x200b8e28 +d00e1429 NV50_2D.SIFC_DATA = 0xd00e1429 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +20000c2d NV50_2D.SIFC_DATA = 0x20000c2d +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +20000001 NV50_2D.SIFC_DATA = 0x20000001 +040087c0 NV50_2D.SIFC_DATA = 0x40087c0 +30400205 NV50_2D.SIFC_DATA = 0x30400205 +0400c780 NV50_2D.SIFC_DATA = 0x400c780 +3001d7fd NV50_2D.SIFC_DATA = 0x3001d7fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +3000d5fd NV50_2D.SIFC_DATA = 0x3000d5fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +d00e1629 NV50_2D.SIFC_DATA = 0xd00e1629 +a0c00780 NV50_2D.SIFC_DATA = 0xa0c00780 +20000811 NV50_2D.SIFC_DATA = 0x20000811 +04014780 NV50_2D.SIFC_DATA = 0x4014780 +3001d7fd NV50_2D.SIFC_DATA = 0x3001d7fd +64210148 NV50_2D.SIFC_DATA = 0x64210148 +2007901c NV50_2D.SIFC_DATA = 0x2007901c +20068a18 NV50_2D.SIFC_DATA = 0x20068a18 +10221003 NV50_2D.SIFC_DATA = 0x10221003 +00000280 NV50_2D.SIFC_DATA = 0x280 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000780 NV50_2D.SIFC_DATA = 0x780 +307cd3fd NV50_2D.SIFC_DATA = 0x307cd3fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +a0004825 NV50_2D.SIFC_DATA = 0xa0004825 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +3008d1fd NV50_2D.SIFC_DATA = 0x3008d1fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +203f9225 NV50_2D.SIFC_DATA = 0x203f9225 +0fffffff NV50_2D.SIFC_DATA = 0xfffffff +307cd3fd NV50_2D.SIFC_DATA = 0x307cd3fd +64210148 NV50_2D.SIFC_DATA = 0x64210148 +30090bfd NV50_2D.SIFC_DATA = 0x30090bfd +640082c8 NV50_2D.SIFC_DATA = 0x640082c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +3003d7fd NV50_2D.SIFC_DATA = 0x3003d7fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +3002d5fd NV50_2D.SIFC_DATA = 0x3002d5fd +6420c2c8 NV50_2D.SIFC_DATA = 0x6420c2c8 +3003d7fd NV50_2D.SIFC_DATA = 0x3003d7fd +64204148 NV50_2D.SIFC_DATA = 0x64204148 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000280 NV50_2D.SIFC_DATA = 0x280 +1000dc15 NV50_2D.SIFC_DATA = 0x1000dc15 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +a0004a09 NV50_2D.SIFC_DATA = 0xa0004a09 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +1000d80d NV50_2D.SIFC_DATA = 0x1000d80d +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +400b0828 NV50_2D.SIFC_DATA = 0x400b0828 +40040e24 NV50_2D.SIFC_DATA = 0x40040e24 +30101429 NV50_2D.SIFC_DATA = 0x30101429 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +30101225 NV50_2D.SIFC_DATA = 0x30101225 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +600a0829 NV50_2D.SIFC_DATA = 0x600a0829 +00028780 NV50_2D.SIFC_DATA = 0x28780 +60040c15 NV50_2D.SIFC_DATA = 0x60040c15 +00024780 NV50_2D.SIFC_DATA = 0x24780 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +10000825 NV50_2D.SIFC_DATA = 0x10000825 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +d0801211 NV50_2D.SIFC_DATA = 0xd0801211 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +30048811 NV50_2D.SIFC_DATA = 0x30048811 +00000003 NV50_2D.SIFC_DATA = 0x3 +d0800811 NV50_2D.SIFC_DATA = 0xd0800811 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +300411fd NV50_2D.SIFC_DATA = 0x300411fd +640187c8 NV50_2D.SIFC_DATA = 0x640187c8 +20001011 NV50_2D.SIFC_DATA = 0x20001011 +0401c500 NV50_2D.SIFC_DATA = 0x401c500 +d00e0811 NV50_2D.SIFC_DATA = 0xd00e0811 +80000500 NV50_2D.SIFC_DATA = 0x80000500 +2000102d NV50_2D.SIFC_DATA = 0x2000102d +04018500 NV50_2D.SIFC_DATA = 0x4018500 +d00e1611 NV50_2D.SIFC_DATA = 0xd00e1611 +a0000500 NV50_2D.SIFC_DATA = 0xa0000500 +2000d011 NV50_2D.SIFC_DATA = 0x2000d011 +04218780 NV50_2D.SIFC_DATA = 0x4218780 +d0800811 NV50_2D.SIFC_DATA = 0xd0800811 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +300411fd NV50_2D.SIFC_DATA = 0x300411fd +640187c8 NV50_2D.SIFC_DATA = 0x640187c8 +a0259003 NV50_2D.SIFC_DATA = 0xa0259003 +00000000 NV50_2D.SIFC_DATA = 0 +10259003 NV50_2D.SIFC_DATA = 0x10259003 +00000280 NV50_2D.SIFC_DATA = 0x280 +2148f02c NV50_2D.SIFC_DATA = 0x2148f02c +20079610 NV50_2D.SIFC_DATA = 0x20079610 +203f8811 NV50_2D.SIFC_DATA = 0x203f8811 +0fffffff NV50_2D.SIFC_DATA = 0xfffffff +d00e0811 NV50_2D.SIFC_DATA = 0xd00e0811 +80000780 NV50_2D.SIFC_DATA = 0x80000780 +2000162d NV50_2D.SIFC_DATA = 0x2000162d +04018780 NV50_2D.SIFC_DATA = 0x4018780 +203f962d NV50_2D.SIFC_DATA = 0x203f962d +0fffffff NV50_2D.SIFC_DATA = 0xfffffff +d00e1611 NV50_2D.SIFC_DATA = 0xd00e1611 +a0000780 NV50_2D.SIFC_DATA = 0xa0000780 +20000001 NV50_2D.SIFC_DATA = 0x20000001 +040087c2 NV50_2D.SIFC_DATA = 0x40087c2 +30400205 NV50_2D.SIFC_DATA = 0x30400205 +0400c780 NV50_2D.SIFC_DATA = 0x400c780 +3001d7fd NV50_2D.SIFC_DATA = 0x3001d7fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +3000d5fd NV50_2D.SIFC_DATA = 0x3000d5fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +20001225 NV50_2D.SIFC_DATA = 0x20001225 +04014780 NV50_2D.SIFC_DATA = 0x4014780 +3001d7fd NV50_2D.SIFC_DATA = 0x3001d7fd +64210148 NV50_2D.SIFC_DATA = 0x64210148 +2007941c NV50_2D.SIFC_DATA = 0x2007941c +20068a18 NV50_2D.SIFC_DATA = 0x20068a18 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000004 NV50_2D.SIFC_WIDTH = 4 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc1300 NV50_2D.DST_ADDRESS_LOW = 0xfffc1300 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40108860 size 4, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10246003 NV50_2D.SIFC_DATA = 0x10246003 +00000280 NV50_2D.SIFC_DATA = 0x280 +f0000001 NV50_2D.SIFC_DATA = 0xf0000001 +e0000001 NV50_2D.SIFC_DATA = 0xe0000001 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000000e NVA3_COMPUTE.QUERY_SEQUENCE = 0xe +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000000f NVA3_COMPUTE.QUERY_SEQUENCE = 0xf +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0d00 NV50_2D.DST_ADDRESS_LOW = 0xfffc0d00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +41008860 size 64, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004205 NV50_2D.SIFC_DATA = 0x10004205 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1000e205 NV50_2D.SIFC_DATA = 0x1000e205 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +60014c01 NV50_2D.SIFC_DATA = 0x60014c01 +00208780 NV50_2D.SIFC_DATA = 0x208780 +d0010009 NV50_2D.SIFC_DATA = 0xd0010009 +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +3000e005 NV50_2D.SIFC_DATA = 0x3000e005 +042007c0 NV50_2D.SIFC_DATA = 0x42007c0 +3040f80d NV50_2D.SIFC_DATA = 0x3040f80d +04008780 NV50_2D.SIFC_DATA = 0x4008780 +307c0209 NV50_2D.SIFC_DATA = 0x307c0209 +64018780 NV50_2D.SIFC_DATA = 0x64018780 +307c0601 NV50_2D.SIFC_DATA = 0x307c0601 +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +d0020015 NV50_2D.SIFC_DATA = 0xd0020015 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +a0004e01 NV50_2D.SIFC_DATA = 0xa0004e01 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +3001d021 NV50_2D.SIFC_DATA = 0x3001d021 +64210780 NV50_2D.SIFC_DATA = 0x64210780 +3003d209 NV50_2D.SIFC_DATA = 0x3003d209 +64208780 NV50_2D.SIFC_DATA = 0x64208780 +307cd61d NV50_2D.SIFC_DATA = 0x307cd61d +64208780 NV50_2D.SIFC_DATA = 0x64208780 +3000d419 NV50_2D.SIFC_DATA = 0x3000d419 +64210780 NV50_2D.SIFC_DATA = 0x64210780 +307c0611 NV50_2D.SIFC_DATA = 0x307c0611 +6c010780 NV50_2D.SIFC_DATA = 0x6c010780 +d0080409 NV50_2D.SIFC_DATA = 0xd0080409 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +3003d20d NV50_2D.SIFC_DATA = 0x3003d20d +64210780 NV50_2D.SIFC_DATA = 0x64210780 +d0060e19 NV50_2D.SIFC_DATA = 0xd0060e19 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0050815 NV50_2D.SIFC_DATA = 0xd0050815 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +307cd611 NV50_2D.SIFC_DATA = 0x307cd611 +64210780 NV50_2D.SIFC_DATA = 0x64210780 +d002060d NV50_2D.SIFC_DATA = 0xd002060d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d0060809 NV50_2D.SIFC_DATA = 0xd0060809 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d0030a0d NV50_2D.SIFC_DATA = 0xd0030a0d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d00305fd NV50_2D.SIFC_DATA = 0xd00305fd +040007c8 NV50_2D.SIFC_DATA = 0x40007c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +1000dc09 NV50_2D.SIFC_DATA = 0x1000dc09 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +6002000d NV50_2D.SIFC_DATA = 0x6002000d +60004780 NV50_2D.SIFC_DATA = 0x60004780 +1100f808 NV50_2D.SIFC_DATA = 0x1100f808 +2103ec0c NV50_2D.SIFC_DATA = 0x2103ec0c +60000405 NV50_2D.SIFC_DATA = 0x60000405 +60004780 NV50_2D.SIFC_DATA = 0x60004780 +d00e0601 NV50_2D.SIFC_DATA = 0xd00e0601 +80000780 NV50_2D.SIFC_DATA = 0x80000780 +2000c805 NV50_2D.SIFC_DATA = 0x2000c805 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000002 NV50_2D.SIFC_WIDTH = 2 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0e00 NV50_2D.DST_ADDRESS_LOW = 0xfffc0e00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40088860 size 2, subchannel 4 (0x5c0000d3), offset 0x0860, constant +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0000781 NV50_2D.SIFC_DATA = 0xa0000781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000010 NVA3_COMPUTE.QUERY_SEQUENCE = 0x10 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000011 NVA3_COMPUTE.QUERY_SEQUENCE = 0x11 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000036 NV50_2D.SIFC_WIDTH = 54 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0c00 NV50_2D.DST_ADDRESS_LOW = 0xfffc0c00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40d88860 size 54, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004205 NV50_2D.SIFC_DATA = 0x10004205 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1000e205 NV50_2D.SIFC_DATA = 0x1000e205 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +60014c01 NV50_2D.SIFC_DATA = 0x60014c01 +00208780 NV50_2D.SIFC_DATA = 0x208780 +d0010009 NV50_2D.SIFC_DATA = 0xd0010009 +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +3000e005 NV50_2D.SIFC_DATA = 0x3000e005 +042007c0 NV50_2D.SIFC_DATA = 0x42007c0 +3040f809 NV50_2D.SIFC_DATA = 0x3040f809 +04008780 NV50_2D.SIFC_DATA = 0x4008780 +10208001 NV50_2D.SIFC_DATA = 0x10208001 +00000003 NV50_2D.SIFC_DATA = 0x3 +301e020d NV50_2D.SIFC_DATA = 0x301e020d +e4100780 NV50_2D.SIFC_DATA = 0xe4100780 +30020409 NV50_2D.SIFC_DATA = 0x30020409 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +210001fd NV50_2D.SIFC_DATA = 0x210001fd +044007c8 NV50_2D.SIFC_DATA = 0x44007c8 +d0030401 NV50_2D.SIFC_DATA = 0xd0030401 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +1000f801 NV50_2D.SIFC_DATA = 0x1000f801 +0403c980 NV50_2D.SIFC_DATA = 0x403c980 +30020211 NV50_2D.SIFC_DATA = 0x30020211 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +3000d3fd NV50_2D.SIFC_DATA = 0x3000d3fd +6c2087c8 NV50_2D.SIFC_DATA = 0x6c2087c8 +3004d1fd NV50_2D.SIFC_DATA = 0x3004d1fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +3000d3fd NV50_2D.SIFC_DATA = 0x3000d3fd +6c210148 NV50_2D.SIFC_DATA = 0x6c210148 +307c09fd NV50_2D.SIFC_DATA = 0x307c09fd +6c0182c8 NV50_2D.SIFC_DATA = 0x6c0182c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +a0004e15 NV50_2D.SIFC_DATA = 0xa0004e15 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +1100fc0c NV50_2D.SIFC_DATA = 0x1100fc0c +1100ec04 NV50_2D.SIFC_DATA = 0x1100ec04 +1100f808 NV50_2D.SIFC_DATA = 0x1100f808 +1100e800 NV50_2D.SIFC_DATA = 0x1100e800 +60030a05 NV50_2D.SIFC_DATA = 0x60030a05 +60004780 NV50_2D.SIFC_DATA = 0x60004780 +60020a01 NV50_2D.SIFC_DATA = 0x60020a01 +60000780 NV50_2D.SIFC_DATA = 0x60000780 +20018808 NV50_2D.SIFC_DATA = 0x20018808 +20008804 NV50_2D.SIFC_DATA = 0x20008804 +d00e0401 NV50_2D.SIFC_DATA = 0xd00e0401 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000012 NVA3_COMPUTE.QUERY_SEQUENCE = 0x12 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000013 NVA3_COMPUTE.QUERY_SEQUENCE = 0x13 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000036 NV50_2D.SIFC_WIDTH = 54 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0b00 NV50_2D.DST_ADDRESS_LOW = 0xfffc0b00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40d88860 size 54, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004205 NV50_2D.SIFC_DATA = 0x10004205 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1000e205 NV50_2D.SIFC_DATA = 0x1000e205 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +60014c01 NV50_2D.SIFC_DATA = 0x60014c01 +00208780 NV50_2D.SIFC_DATA = 0x208780 +d0010009 NV50_2D.SIFC_DATA = 0xd0010009 +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +3000e005 NV50_2D.SIFC_DATA = 0x3000e005 +042007c0 NV50_2D.SIFC_DATA = 0x42007c0 +3040f809 NV50_2D.SIFC_DATA = 0x3040f809 +04008780 NV50_2D.SIFC_DATA = 0x4008780 +10208001 NV50_2D.SIFC_DATA = 0x10208001 +00000003 NV50_2D.SIFC_DATA = 0x3 +301e020d NV50_2D.SIFC_DATA = 0x301e020d +e4100780 NV50_2D.SIFC_DATA = 0xe4100780 +30020409 NV50_2D.SIFC_DATA = 0x30020409 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +210001fd NV50_2D.SIFC_DATA = 0x210001fd +044007c8 NV50_2D.SIFC_DATA = 0x44007c8 +d0030401 NV50_2D.SIFC_DATA = 0xd0030401 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +1000f801 NV50_2D.SIFC_DATA = 0x1000f801 +0403c980 NV50_2D.SIFC_DATA = 0x403c980 +3002020d NV50_2D.SIFC_DATA = 0x3002020d +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +3000d3fd NV50_2D.SIFC_DATA = 0x3000d3fd +6c2087c8 NV50_2D.SIFC_DATA = 0x6c2087c8 +3003d1fd NV50_2D.SIFC_DATA = 0x3003d1fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +3000d3fd NV50_2D.SIFC_DATA = 0x3000d3fd +6c210148 NV50_2D.SIFC_DATA = 0x6c210148 +307c07fd NV50_2D.SIFC_DATA = 0x307c07fd +6c0182c8 NV50_2D.SIFC_DATA = 0x6c0182c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +1000d809 NV50_2D.SIFC_DATA = 0x1000d809 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +a0004e11 NV50_2D.SIFC_DATA = 0xa0004e11 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +1100ec04 NV50_2D.SIFC_DATA = 0x1100ec04 +1100e800 NV50_2D.SIFC_DATA = 0x1100e800 +60020805 NV50_2D.SIFC_DATA = 0x60020805 +60004780 NV50_2D.SIFC_DATA = 0x60004780 +60020801 NV50_2D.SIFC_DATA = 0x60020801 +60000780 NV50_2D.SIFC_DATA = 0x60000780 +20018608 NV50_2D.SIFC_DATA = 0x20018608 +20008604 NV50_2D.SIFC_DATA = 0x20008604 +d00e0401 NV50_2D.SIFC_DATA = 0xd00e0401 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000014 NVA3_COMPUTE.QUERY_SEQUENCE = 0x14 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000015 NVA3_COMPUTE.QUERY_SEQUENCE = 0x15 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0900 NV50_2D.DST_ADDRESS_LOW = 0xfffc0900 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +41008860 size 64, subchannel 4 (0x5c0000d3), offset 0x0860, constant +1000dc0d NV50_2D.SIFC_DATA = 0x1000dc0d +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +a0004e09 NV50_2D.SIFC_DATA = 0xa0004e09 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +1000d805 NV50_2D.SIFC_DATA = 0x1000d805 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +40070810 NV50_2D.SIFC_DATA = 0x40070810 +40040614 NV50_2D.SIFC_DATA = 0x40040614 +307cd7fd NV50_2D.SIFC_DATA = 0x307cd7fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +30100811 NV50_2D.SIFC_DATA = 0x30100811 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +30100a15 NV50_2D.SIFC_DATA = 0x30100a15 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +3002d5fd NV50_2D.SIFC_DATA = 0x3002d5fd +6420c2c8 NV50_2D.SIFC_DATA = 0x6420c2c8 +60060811 NV50_2D.SIFC_DATA = 0x60060811 +00010780 NV50_2D.SIFC_DATA = 0x10780 +60040405 NV50_2D.SIFC_DATA = 0x60040405 +00014780 NV50_2D.SIFC_DATA = 0x14780 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +307cd7fd NV50_2D.SIFC_DATA = 0x307cd7fd +64204148 NV50_2D.SIFC_DATA = 0x64204148 +2104ec18 NV50_2D.SIFC_DATA = 0x2104ec18 +2101e81c NV50_2D.SIFC_DATA = 0x2101e81c +10000005 NV50_2D.SIFC_DATA = 0x10000005 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000280 NV50_2D.SIFC_DATA = 0x280 +10004201 NV50_2D.SIFC_DATA = 0x10004201 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000411 NV50_2D.SIFC_DATA = 0xa0000411 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1000e205 NV50_2D.SIFC_DATA = 0x1000e205 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +60004c11 NV50_2D.SIFC_DATA = 0x60004c11 +00210780 NV50_2D.SIFC_DATA = 0x210780 +d0010001 NV50_2D.SIFC_DATA = 0xd0010001 +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +3000e015 NV50_2D.SIFC_DATA = 0x3000e015 +042107c0 NV50_2D.SIFC_DATA = 0x42107c0 +3040f805 NV50_2D.SIFC_DATA = 0x3040f805 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +10208011 NV50_2D.SIFC_DATA = 0x10208011 +00000003 NV50_2D.SIFC_DATA = 0x3 +301e0a01 NV50_2D.SIFC_DATA = 0x301e0a01 +e4100780 NV50_2D.SIFC_DATA = 0xe4100780 +30020205 NV50_2D.SIFC_DATA = 0x30020205 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +210009fd NV50_2D.SIFC_DATA = 0x210009fd +044007c8 NV50_2D.SIFC_DATA = 0x44007c8 +d0000225 NV50_2D.SIFC_DATA = 0xd0000225 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +1000f825 NV50_2D.SIFC_DATA = 0x1000f825 +0403c980 NV50_2D.SIFC_DATA = 0x403c980 +1000dc05 NV50_2D.SIFC_DATA = 0x1000dc05 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +30020a21 NV50_2D.SIFC_DATA = 0x30020a21 +c41007d0 NV50_2D.SIFC_DATA = 0xc41007d0 +3009d3fd NV50_2D.SIFC_DATA = 0x3009d3fd +6c2087c8 NV50_2D.SIFC_DATA = 0x6c2087c8 +a0004a11 NV50_2D.SIFC_DATA = 0xa0004a11 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000038 NV50_2D.SIFC_WIDTH = 56 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0a00 NV50_2D.DST_ADDRESS_LOW = 0xfffc0a00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40e08860 size 56, subchannel 4 (0x5c0000d3), offset 0x0860, constant +1000d801 NV50_2D.SIFC_DATA = 0x1000d801 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +3008d1fd NV50_2D.SIFC_DATA = 0x3008d1fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +3009d3fd NV50_2D.SIFC_DATA = 0x3009d3fd +6c210148 NV50_2D.SIFC_DATA = 0x6c210148 +40031024 NV50_2D.SIFC_DATA = 0x40031024 +4008022c NV50_2D.SIFC_DATA = 0x4008022c +1000f829 NV50_2D.SIFC_DATA = 0x1000f829 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1000f815 NV50_2D.SIFC_DATA = 0x1000f815 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +30101225 NV50_2D.SIFC_DATA = 0x30101225 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +3010162d NV50_2D.SIFC_DATA = 0x3010162d +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +10000229 NV50_2D.SIFC_DATA = 0x10000229 +2440de00 NV50_2D.SIFC_DATA = 0x2440de00 +10000215 NV50_2D.SIFC_DATA = 0x10000215 +2440c280 NV50_2D.SIFC_DATA = 0x2440c280 +60021025 NV50_2D.SIFC_DATA = 0x60021025 +00024780 NV50_2D.SIFC_DATA = 0x24780 +60080005 NV50_2D.SIFC_DATA = 0x60080005 +0002c780 NV50_2D.SIFC_DATA = 0x2c780 +d00a0a29 NV50_2D.SIFC_DATA = 0xd00a0a29 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +1000f815 NV50_2D.SIFC_DATA = 0x1000f815 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +307c15fd NV50_2D.SIFC_DATA = 0x307c15fd +6c0087c8 NV50_2D.SIFC_DATA = 0x6c0087c8 +2000102d NV50_2D.SIFC_DATA = 0x2000102d +04018500 NV50_2D.SIFC_DATA = 0x4018500 +20000e01 NV50_2D.SIFC_DATA = 0x20000e01 +04020500 NV50_2D.SIFC_DATA = 0x4020500 +d00e162d NV50_2D.SIFC_DATA = 0xd00e162d +80c00500 NV50_2D.SIFC_DATA = 0x80c00500 +d00e002d NV50_2D.SIFC_DATA = 0xd00e002d +a0c00500 NV50_2D.SIFC_DATA = 0xa0c00500 +20000409 NV50_2D.SIFC_DATA = 0x20000409 +040107c0 NV50_2D.SIFC_DATA = 0x40107c0 +30400601 NV50_2D.SIFC_DATA = 0x30400601 +04014780 NV50_2D.SIFC_DATA = 0x4014780 +3000d7fd NV50_2D.SIFC_DATA = 0x3000d7fd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +3002d5fd NV50_2D.SIFC_DATA = 0x3002d5fd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +3000d7fd NV50_2D.SIFC_DATA = 0x3000d7fd +64210148 NV50_2D.SIFC_DATA = 0x64210148 +2007821c NV50_2D.SIFC_DATA = 0x2007821c +20069218 NV50_2D.SIFC_DATA = 0x20069218 +1000000d NV50_2D.SIFC_DATA = 0x1000000d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1014e003 NV50_2D.SIFC_DATA = 0x1014e003 +00000280 NV50_2D.SIFC_DATA = 0x280 +f0000001 NV50_2D.SIFC_DATA = 0xf0000001 +e0000001 NV50_2D.SIFC_DATA = 0xe0000001 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000016 NVA3_COMPUTE.QUERY_SEQUENCE = 0x16 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000a8 2010408c +# out of band: 000000ac 00030600 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000017 NVA3_COMPUTE.QUERY_SEQUENCE = 0x17 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000b0 20104390 +# out of band: 000000b4 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000024 NV50_2D.SIFC_WIDTH = 36 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0800 NV50_2D.DST_ADDRESS_LOW = 0xfffc0800 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40908860 size 36, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +d0800205 NV50_2D.SIFC_DATA = 0xd0800205 +00400780 NV50_2D.SIFC_DATA = 0x400780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +10004401 NV50_2D.SIFC_DATA = 0x10004401 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a000020d NV50_2D.SIFC_DATA = 0xa000020d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +60024c05 NV50_2D.SIFC_DATA = 0x60024c05 +00208780 NV50_2D.SIFC_DATA = 0x208780 +60004e01 NV50_2D.SIFC_DATA = 0x60004e01 +0020c780 NV50_2D.SIFC_DATA = 0x20c780 +3001c9fd NV50_2D.SIFC_DATA = 0x3001c9fd +642107c8 NV50_2D.SIFC_DATA = 0x642107c8 +3000cbfd NV50_2D.SIFC_DATA = 0x3000cbfd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +2000ce0d NV50_2D.SIFC_DATA = 0x2000ce0d +04200780 NV50_2D.SIFC_DATA = 0x4200780 +2000cc09 NV50_2D.SIFC_DATA = 0x2000cc09 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +2101f010 NV50_2D.SIFC_DATA = 0x2101f010 +10000c0c NV50_2D.SIFC_DATA = 0x10000c0c +10000809 NV50_2D.SIFC_DATA = 0x10000809 +0003c780 NV50_2D.SIFC_DATA = 0x3c780 +2000d209 NV50_2D.SIFC_DATA = 0x2000d209 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +d0000201 NV50_2D.SIFC_DATA = 0xd0000201 +80000780 NV50_2D.SIFC_DATA = 0x80000780 +1000080c NV50_2D.SIFC_DATA = 0x1000080c +10001008 NV50_2D.SIFC_DATA = 0x10001008 +d0010201 NV50_2D.SIFC_DATA = 0xd0010201 +a0000781 NV50_2D.SIFC_DATA = 0xa0000781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000018 NVA3_COMPUTE.QUERY_SEQUENCE = 0x18 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000b8 201043ac +# out of band: 000000bc 00012e00 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000019 NVA3_COMPUTE.QUERY_SEQUENCE = 0x19 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000c0 201044d8 +# out of band: 000000c4 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000026 NV50_2D.SIFC_WIDTH = 38 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0700 NV50_2D.DST_ADDRESS_LOW = 0xfffc0700 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40988860 size 38, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0800205 NV50_2D.SIFC_DATA = 0xd0800205 +00400780 NV50_2D.SIFC_DATA = 0x400780 +60024c05 NV50_2D.SIFC_DATA = 0x60024c05 +00208780 NV50_2D.SIFC_DATA = 0x208780 +10004401 NV50_2D.SIFC_DATA = 0x10004401 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000209 NV50_2D.SIFC_DATA = 0xa0000209 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +30010205 NV50_2D.SIFC_DATA = 0x30010205 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60004e01 NV50_2D.SIFC_DATA = 0x60004e01 +00208780 NV50_2D.SIFC_DATA = 0x208780 +3001c9fd NV50_2D.SIFC_DATA = 0x3001c9fd +642107c8 NV50_2D.SIFC_DATA = 0x642107c8 +3000cbfd NV50_2D.SIFC_DATA = 0x3000cbfd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +2000ce0d NV50_2D.SIFC_DATA = 0x2000ce0d +04200780 NV50_2D.SIFC_DATA = 0x4200780 +2000cc09 NV50_2D.SIFC_DATA = 0x2000cc09 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +2101f010 NV50_2D.SIFC_DATA = 0x2101f010 +10000c0c NV50_2D.SIFC_DATA = 0x10000c0c +10000809 NV50_2D.SIFC_DATA = 0x10000809 +0003c780 NV50_2D.SIFC_DATA = 0x3c780 +2000d209 NV50_2D.SIFC_DATA = 0x2000d209 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +d0000201 NV50_2D.SIFC_DATA = 0xd0000201 +80400780 NV50_2D.SIFC_DATA = 0x80400780 +1000080c NV50_2D.SIFC_DATA = 0x1000080c +10001008 NV50_2D.SIFC_DATA = 0x10001008 +d0010201 NV50_2D.SIFC_DATA = 0xd0010201 +a0400781 NV50_2D.SIFC_DATA = 0xa0400781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000001a NVA3_COMPUTE.QUERY_SEQUENCE = 0x1a +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000c8 201044f4 +# out of band: 000000cc 00013600 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000001b NVA3_COMPUTE.QUERY_SEQUENCE = 0x1b +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000d0 20104628 +# out of band: 000000d4 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000026 NV50_2D.SIFC_WIDTH = 38 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0600 NV50_2D.DST_ADDRESS_LOW = 0xfffc0600 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40988860 size 38, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0800205 NV50_2D.SIFC_DATA = 0xd0800205 +00400780 NV50_2D.SIFC_DATA = 0x400780 +60024c05 NV50_2D.SIFC_DATA = 0x60024c05 +00208780 NV50_2D.SIFC_DATA = 0x208780 +10004401 NV50_2D.SIFC_DATA = 0x10004401 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000209 NV50_2D.SIFC_DATA = 0xa0000209 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +30020205 NV50_2D.SIFC_DATA = 0x30020205 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60004e01 NV50_2D.SIFC_DATA = 0x60004e01 +00208780 NV50_2D.SIFC_DATA = 0x208780 +3001c9fd NV50_2D.SIFC_DATA = 0x3001c9fd +642107c8 NV50_2D.SIFC_DATA = 0x642107c8 +3000cbfd NV50_2D.SIFC_DATA = 0x3000cbfd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +2000cc09 NV50_2D.SIFC_DATA = 0x2000cc09 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +2000ce0d NV50_2D.SIFC_DATA = 0x2000ce0d +04200780 NV50_2D.SIFC_DATA = 0x4200780 +2000d011 NV50_2D.SIFC_DATA = 0x2000d011 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +2000d201 NV50_2D.SIFC_DATA = 0x2000d201 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +10000c0c NV50_2D.SIFC_DATA = 0x10000c0c +10000808 NV50_2D.SIFC_DATA = 0x10000808 +10000004 NV50_2D.SIFC_DATA = 0x10000004 +10001000 NV50_2D.SIFC_DATA = 0x10001000 +d0000205 NV50_2D.SIFC_DATA = 0xd0000205 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d0010005 NV50_2D.SIFC_DATA = 0xd0010005 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000001c NVA3_COMPUTE.QUERY_SEQUENCE = 0x1c +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000d8 20104644 +# out of band: 000000dc 00013600 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000001d NVA3_COMPUTE.QUERY_SEQUENCE = 0x1d +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000e0 20104778 +# out of band: 000000e4 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +0000002a NV50_2D.SIFC_WIDTH = 42 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0500 NV50_2D.DST_ADDRESS_LOW = 0xfffc0500 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40a88860 size 42, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +d0800205 NV50_2D.SIFC_DATA = 0xd0800205 +00400780 NV50_2D.SIFC_DATA = 0x400780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +10004401 NV50_2D.SIFC_DATA = 0x10004401 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a000020d NV50_2D.SIFC_DATA = 0xa000020d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +60024c09 NV50_2D.SIFC_DATA = 0x60024c09 +00208780 NV50_2D.SIFC_DATA = 0x208780 +60004e05 NV50_2D.SIFC_DATA = 0x60004e05 +0020c780 NV50_2D.SIFC_DATA = 0x20c780 +3002cdfd NV50_2D.SIFC_DATA = 0x3002cdfd +642107c8 NV50_2D.SIFC_DATA = 0x642107c8 +3001cffd NV50_2D.SIFC_DATA = 0x3001cffd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +1000d001 NV50_2D.SIFC_DATA = 0x1000d001 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +4001040d NV50_2D.SIFC_DATA = 0x4001040d +00000780 NV50_2D.SIFC_DATA = 0x780 +6000060d NV50_2D.SIFC_DATA = 0x6000060d +0000c780 NV50_2D.SIFC_DATA = 0xc780 +3010060d NV50_2D.SIFC_DATA = 0x3010060d +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60000401 NV50_2D.SIFC_DATA = 0x60000401 +0000c780 NV50_2D.SIFC_DATA = 0xc780 +20008400 NV50_2D.SIFC_DATA = 0x20008400 +2102f408 NV50_2D.SIFC_DATA = 0x2102f408 +2000c801 NV50_2D.SIFC_DATA = 0x2000c801 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +2000d605 NV50_2D.SIFC_DATA = 0x2000d605 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +d00e0001 NV50_2D.SIFC_DATA = 0xd00e0001 +80000780 NV50_2D.SIFC_DATA = 0x80000780 +1000040c NV50_2D.SIFC_DATA = 0x1000040c +10000808 NV50_2D.SIFC_DATA = 0x10000808 +d0000201 NV50_2D.SIFC_DATA = 0xd0000201 +a0000781 NV50_2D.SIFC_DATA = 0xa0000781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000001e NVA3_COMPUTE.QUERY_SEQUENCE = 0x1e +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000e8 20104794 +# out of band: 000000ec 00014600 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000001f NVA3_COMPUTE.QUERY_SEQUENCE = 0x1f +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000f0 201048d8 +# out of band: 000000f4 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000036 NV50_2D.SIFC_WIDTH = 54 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0400 NV50_2D.DST_ADDRESS_LOW = 0xfffc0400 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40d88860 size 54, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0800205 NV50_2D.SIFC_DATA = 0xd0800205 +00400780 NV50_2D.SIFC_DATA = 0x400780 +60024c05 NV50_2D.SIFC_DATA = 0x60024c05 +00208780 NV50_2D.SIFC_DATA = 0x208780 +10004401 NV50_2D.SIFC_DATA = 0x10004401 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a000020d NV50_2D.SIFC_DATA = 0xa000020d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +30010209 NV50_2D.SIFC_DATA = 0x30010209 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60004e01 NV50_2D.SIFC_DATA = 0x60004e01 +0020c780 NV50_2D.SIFC_DATA = 0x20c780 +3002cdfd NV50_2D.SIFC_DATA = 0x3002cdfd +642107c8 NV50_2D.SIFC_DATA = 0x642107c8 +3000cffd NV50_2D.SIFC_DATA = 0x3000cffd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +3001d00d NV50_2D.SIFC_DATA = 0x3001d00d +e4300780 NV50_2D.SIFC_DATA = 0xe4300780 +301fd211 NV50_2D.SIFC_DATA = 0x301fd211 +c4300780 NV50_2D.SIFC_DATA = 0xc4300780 +d004060d NV50_2D.SIFC_DATA = 0xd004060d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +a000f9fd NV50_2D.SIFC_DATA = 0xa000f9fd +040047c8 NV50_2D.SIFC_DATA = 0x40047c8 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c280 NV50_2D.SIFC_DATA = 0x403c280 +40070011 NV50_2D.SIFC_DATA = 0x40070011 +00000780 NV50_2D.SIFC_DATA = 0x780 +60060211 NV50_2D.SIFC_DATA = 0x60060211 +00010780 NV50_2D.SIFC_DATA = 0x10780 +30100811 NV50_2D.SIFC_DATA = 0x30100811 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +6006000d NV50_2D.SIFC_DATA = 0x6006000d +00010780 NV50_2D.SIFC_DATA = 0x10780 +20000605 NV50_2D.SIFC_DATA = 0x20000605 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +30010205 NV50_2D.SIFC_DATA = 0x30010205 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +2102f408 NV50_2D.SIFC_DATA = 0x2102f408 +2101e804 NV50_2D.SIFC_DATA = 0x2101e804 +2000d60d NV50_2D.SIFC_DATA = 0x2000d60d +04200780 NV50_2D.SIFC_DATA = 0x4200780 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +80400780 NV50_2D.SIFC_DATA = 0x80400780 +10000c0c NV50_2D.SIFC_DATA = 0x10000c0c +10000808 NV50_2D.SIFC_DATA = 0x10000808 +d0000201 NV50_2D.SIFC_DATA = 0xd0000201 +a0400781 NV50_2D.SIFC_DATA = 0xa0400781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000020 NVA3_COMPUTE.QUERY_SEQUENCE = 0x20 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000000f8 201048f4 +# out of band: 000000fc 00017600 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000021 NVA3_COMPUTE.QUERY_SEQUENCE = 0x21 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000100 20104a68 +# out of band: 00000104 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000034 NV50_2D.SIFC_WIDTH = 52 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0300 NV50_2D.DST_ADDRESS_LOW = 0xfffc0300 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40d08860 size 52, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0800205 NV50_2D.SIFC_DATA = 0xd0800205 +00400780 NV50_2D.SIFC_DATA = 0x400780 +60024c05 NV50_2D.SIFC_DATA = 0x60024c05 +00208780 NV50_2D.SIFC_DATA = 0x208780 +10004401 NV50_2D.SIFC_DATA = 0x10004401 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a000020d NV50_2D.SIFC_DATA = 0xa000020d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +30020209 NV50_2D.SIFC_DATA = 0x30020209 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60004e01 NV50_2D.SIFC_DATA = 0x60004e01 +0020c780 NV50_2D.SIFC_DATA = 0x20c780 +3002cdfd NV50_2D.SIFC_DATA = 0x3002cdfd +642107c8 NV50_2D.SIFC_DATA = 0x642107c8 +3000cffd NV50_2D.SIFC_DATA = 0x3000cffd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +3002d00d NV50_2D.SIFC_DATA = 0x3002d00d +e4300780 NV50_2D.SIFC_DATA = 0xe4300780 +301ed211 NV50_2D.SIFC_DATA = 0x301ed211 +c4300780 NV50_2D.SIFC_DATA = 0xc4300780 +d004060d NV50_2D.SIFC_DATA = 0xd004060d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +a000f9fd NV50_2D.SIFC_DATA = 0xa000f9fd +040047c8 NV50_2D.SIFC_DATA = 0x40047c8 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c280 NV50_2D.SIFC_DATA = 0x403c280 +40070011 NV50_2D.SIFC_DATA = 0x40070011 +00000780 NV50_2D.SIFC_DATA = 0x780 +60060211 NV50_2D.SIFC_DATA = 0x60060211 +00010780 NV50_2D.SIFC_DATA = 0x10780 +30100811 NV50_2D.SIFC_DATA = 0x30100811 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +6006000d NV50_2D.SIFC_DATA = 0x6006000d +00010780 NV50_2D.SIFC_DATA = 0x10780 +20018604 NV50_2D.SIFC_DATA = 0x20018604 +2100f60c NV50_2D.SIFC_DATA = 0x2100f60c +2000d401 NV50_2D.SIFC_DATA = 0x2000d401 +04208780 NV50_2D.SIFC_DATA = 0x4208780 +30020205 NV50_2D.SIFC_DATA = 0x30020205 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +10000c04 NV50_2D.SIFC_DATA = 0x10000c04 +2101e804 NV50_2D.SIFC_DATA = 0x2101e804 +d00e0205 NV50_2D.SIFC_DATA = 0xd00e0205 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d0000005 NV50_2D.SIFC_DATA = 0xd0000005 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000022 NVA3_COMPUTE.QUERY_SEQUENCE = 0x22 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000108 20104a84 +# out of band: 0000010c 00016e00 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000023 NVA3_COMPUTE.QUERY_SEQUENCE = 0x23 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000110 20104bf0 +# out of band: 00000114 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +0000002c NV50_2D.SIFC_WIDTH = 44 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0200 NV50_2D.DST_ADDRESS_LOW = 0xfffc0200 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40b08860 size 44, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +d0800205 NV50_2D.SIFC_DATA = 0xd0800205 +00400780 NV50_2D.SIFC_DATA = 0x400780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +10004401 NV50_2D.SIFC_DATA = 0x10004401 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a000020d NV50_2D.SIFC_DATA = 0xa000020d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +60024c09 NV50_2D.SIFC_DATA = 0x60024c09 +00208780 NV50_2D.SIFC_DATA = 0x208780 +60004e05 NV50_2D.SIFC_DATA = 0x60004e05 +0020c780 NV50_2D.SIFC_DATA = 0x20c780 +3002cdfd NV50_2D.SIFC_DATA = 0x3002cdfd +642107c8 NV50_2D.SIFC_DATA = 0x642107c8 +3001cffd NV50_2D.SIFC_DATA = 0x3001cffd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +1000d001 NV50_2D.SIFC_DATA = 0x1000d001 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +4001040d NV50_2D.SIFC_DATA = 0x4001040d +00000780 NV50_2D.SIFC_DATA = 0x780 +6000060d NV50_2D.SIFC_DATA = 0x6000060d +0000c780 NV50_2D.SIFC_DATA = 0xc780 +2000d615 NV50_2D.SIFC_DATA = 0x2000d615 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +3010060d NV50_2D.SIFC_DATA = 0x3010060d +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +2000d411 NV50_2D.SIFC_DATA = 0x2000d411 +04208780 NV50_2D.SIFC_DATA = 0x4208780 +60000405 NV50_2D.SIFC_DATA = 0x60000405 +0000c780 NV50_2D.SIFC_DATA = 0xc780 +10001404 NV50_2D.SIFC_DATA = 0x10001404 +10001000 NV50_2D.SIFC_DATA = 0x10001000 +20000205 NV50_2D.SIFC_DATA = 0x20000205 +04008780 NV50_2D.SIFC_DATA = 0x4008780 +d0000001 NV50_2D.SIFC_DATA = 0xd0000001 +80000780 NV50_2D.SIFC_DATA = 0x80000780 +2000c805 NV50_2D.SIFC_DATA = 0x2000c805 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0000781 NV50_2D.SIFC_DATA = 0xa0000781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000024 NVA3_COMPUTE.QUERY_SEQUENCE = 0x24 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000118 20104c0c +# out of band: 0000011c 00014e00 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000025 NVA3_COMPUTE.QUERY_SEQUENCE = 0x25 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000120 20104d58 +# out of band: 00000124 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000038 NV50_2D.SIFC_WIDTH = 56 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0100 NV50_2D.DST_ADDRESS_LOW = 0xfffc0100 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40e08860 size 56, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0800205 NV50_2D.SIFC_DATA = 0xd0800205 +00400780 NV50_2D.SIFC_DATA = 0x400780 +60024c05 NV50_2D.SIFC_DATA = 0x60024c05 +00208780 NV50_2D.SIFC_DATA = 0x208780 +10004401 NV50_2D.SIFC_DATA = 0x10004401 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a000020d NV50_2D.SIFC_DATA = 0xa000020d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +30010209 NV50_2D.SIFC_DATA = 0x30010209 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60004e01 NV50_2D.SIFC_DATA = 0x60004e01 +0020c780 NV50_2D.SIFC_DATA = 0x20c780 +3002cdfd NV50_2D.SIFC_DATA = 0x3002cdfd +642107c8 NV50_2D.SIFC_DATA = 0x642107c8 +3000cffd NV50_2D.SIFC_DATA = 0x3000cffd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +3001d00d NV50_2D.SIFC_DATA = 0x3001d00d +e4300780 NV50_2D.SIFC_DATA = 0xe4300780 +301fd211 NV50_2D.SIFC_DATA = 0x301fd211 +c4300780 NV50_2D.SIFC_DATA = 0xc4300780 +d004060d NV50_2D.SIFC_DATA = 0xd004060d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +a000f9fd NV50_2D.SIFC_DATA = 0xa000f9fd +040047c8 NV50_2D.SIFC_DATA = 0x40047c8 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c280 NV50_2D.SIFC_DATA = 0x403c280 +40070011 NV50_2D.SIFC_DATA = 0x40070011 +00000780 NV50_2D.SIFC_DATA = 0x780 +60060215 NV50_2D.SIFC_DATA = 0x60060215 +00010780 NV50_2D.SIFC_DATA = 0x10780 +2000d611 NV50_2D.SIFC_DATA = 0x2000d611 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +30100a15 NV50_2D.SIFC_DATA = 0x30100a15 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +2000d419 NV50_2D.SIFC_DATA = 0x2000d419 +04208780 NV50_2D.SIFC_DATA = 0x4208780 +60060009 NV50_2D.SIFC_DATA = 0x60060009 +00014780 NV50_2D.SIFC_DATA = 0x14780 +10001004 NV50_2D.SIFC_DATA = 0x10001004 +10001800 NV50_2D.SIFC_DATA = 0x10001800 +20000405 NV50_2D.SIFC_DATA = 0x20000405 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d0000001 NV50_2D.SIFC_DATA = 0xd0000001 +80400780 NV50_2D.SIFC_DATA = 0x80400780 +30010205 NV50_2D.SIFC_DATA = 0x30010205 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +2000c805 NV50_2D.SIFC_DATA = 0x2000c805 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0400781 NV50_2D.SIFC_DATA = 0xa0400781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000026 NVA3_COMPUTE.QUERY_SEQUENCE = 0x26 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000128 20104d74 +# out of band: 0000012c 00017e00 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000027 NVA3_COMPUTE.QUERY_SEQUENCE = 0x27 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000130 20104ef0 +# out of band: 00000134 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000038 NV50_2D.SIFC_WIDTH = 56 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc0000 NV50_2D.DST_ADDRESS_LOW = 0xfffc0000 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40e08860 size 56, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0800205 NV50_2D.SIFC_DATA = 0xd0800205 +00400780 NV50_2D.SIFC_DATA = 0x400780 +60024c05 NV50_2D.SIFC_DATA = 0x60024c05 +00208780 NV50_2D.SIFC_DATA = 0x208780 +10004401 NV50_2D.SIFC_DATA = 0x10004401 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a000020d NV50_2D.SIFC_DATA = 0xa000020d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +30020209 NV50_2D.SIFC_DATA = 0x30020209 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60004e01 NV50_2D.SIFC_DATA = 0x60004e01 +0020c780 NV50_2D.SIFC_DATA = 0x20c780 +3002cdfd NV50_2D.SIFC_DATA = 0x3002cdfd +642107c8 NV50_2D.SIFC_DATA = 0x642107c8 +3000cffd NV50_2D.SIFC_DATA = 0x3000cffd +642102c8 NV50_2D.SIFC_DATA = 0x642102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +3002d00d NV50_2D.SIFC_DATA = 0x3002d00d +e4300780 NV50_2D.SIFC_DATA = 0xe4300780 +301ed211 NV50_2D.SIFC_DATA = 0x301ed211 +c4300780 NV50_2D.SIFC_DATA = 0xc4300780 +d004060d NV50_2D.SIFC_DATA = 0xd004060d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +a000f9fd NV50_2D.SIFC_DATA = 0xa000f9fd +040047c8 NV50_2D.SIFC_DATA = 0x40047c8 +1000f80d NV50_2D.SIFC_DATA = 0x1000f80d +0403c280 NV50_2D.SIFC_DATA = 0x403c280 +40070011 NV50_2D.SIFC_DATA = 0x40070011 +00000780 NV50_2D.SIFC_DATA = 0x780 +60060215 NV50_2D.SIFC_DATA = 0x60060215 +00010780 NV50_2D.SIFC_DATA = 0x10780 +2000d611 NV50_2D.SIFC_DATA = 0x2000d611 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +30100a15 NV50_2D.SIFC_DATA = 0x30100a15 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +2000d419 NV50_2D.SIFC_DATA = 0x2000d419 +04208780 NV50_2D.SIFC_DATA = 0x4208780 +60060009 NV50_2D.SIFC_DATA = 0x60060009 +00014780 NV50_2D.SIFC_DATA = 0x14780 +10001004 NV50_2D.SIFC_DATA = 0x10001004 +10001800 NV50_2D.SIFC_DATA = 0x10001800 +20000405 NV50_2D.SIFC_DATA = 0x20000405 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d0000001 NV50_2D.SIFC_DATA = 0xd0000001 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +30020205 NV50_2D.SIFC_DATA = 0x30020205 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +2000c805 NV50_2D.SIFC_DATA = 0x2000c805 +04204780 NV50_2D.SIFC_DATA = 0x4204780 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000028 NVA3_COMPUTE.QUERY_SEQUENCE = 0x28 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000138 20104f0c +# out of band: 0000013c 00017e00 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000029 NVA3_COMPUTE.QUERY_SEQUENCE = 0x29 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000140 20105088 +# out of band: 00000144 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000003 NV50_2D.SIFC_WIDTH = 3 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00101100 NV50_2D.DST_ADDRESS_LOW = 0x101100 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +400c8860 size 3, subchannel 4 (0x5c0000d3), offset 0x0860, constant +00000003 NV50_2D.SIFC_DATA = 0x3 +ffffffff NV50_2D.SIFC_DATA = 0xffffffff +00000001 NV50_2D.SIFC_DATA = 0x1 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000002a NVA3_COMPUTE.QUERY_SEQUENCE = 0x2a +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000148 201050a4 +# out of band: 0000014c 0000aa00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000002 NV50_2D.SIFC_WIDTH = 2 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00101000 NV50_2D.DST_ADDRESS_LOW = 0x101000 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40088860 size 2, subchannel 4 (0x5c0000d3), offset 0x0860, constant +fffffffe NV50_2D.SIFC_DATA = 0xfffffffe +00000001 NV50_2D.SIFC_DATA = 0x1 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000002b NVA3_COMPUTE.QUERY_SEQUENCE = 0x2b +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000150 2010514c +# out of band: 00000154 0000a600 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000003 NV50_2D.SIFC_WIDTH = 3 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100f00 NV50_2D.DST_ADDRESS_LOW = 0x100f00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +400c8860 size 3, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00000003 NV50_2D.SIFC_DATA = 0x3 +fffffffe NV50_2D.SIFC_DATA = 0xfffffffe +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000002c NVA3_COMPUTE.QUERY_SEQUENCE = 0x2c +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000158 201051f0 +# out of band: 0000015c 0000aa00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000002 NV50_2D.SIFC_WIDTH = 2 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100e00 NV50_2D.DST_ADDRESS_LOW = 0x100e00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40088860 size 2, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00000003 NV50_2D.SIFC_DATA = 0x3 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000002d NVA3_COMPUTE.QUERY_SEQUENCE = 0x2d +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000160 20105298 +# out of band: 00000164 0000a600 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100d00 NV50_2D.DST_ADDRESS_LOW = 0x100d00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +fffffffe NV50_2D.SIFC_DATA = 0xfffffffe +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000002e NVA3_COMPUTE.QUERY_SEQUENCE = 0x2e +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000168 2010533c +# out of band: 0000016c 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000002 NV50_2D.SIFC_WIDTH = 2 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100c00 NV50_2D.DST_ADDRESS_LOW = 0x100c00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40088860 size 2, subchannel 4 (0x5c0000d3), offset 0x0860, constant +00000003 NV50_2D.SIFC_DATA = 0x3 +ffffffff NV50_2D.SIFC_DATA = 0xffffffff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000002f NVA3_COMPUTE.QUERY_SEQUENCE = 0x2f +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000170 201053dc +# out of band: 00000174 0000a600 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100b00 NV50_2D.DST_ADDRESS_LOW = 0x100b00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +fffffffe NV50_2D.SIFC_DATA = 0xfffffffe +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000030 NVA3_COMPUTE.QUERY_SEQUENCE = 0x30 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000178 20105480 +# out of band: 0000017c 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100a00 NV50_2D.DST_ADDRESS_LOW = 0x100a00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +fffffffe NV50_2D.SIFC_DATA = 0xfffffffe +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000031 NVA3_COMPUTE.QUERY_SEQUENCE = 0x31 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000180 20105520 +# out of band: 00000184 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000002 NV50_2D.SIFC_WIDTH = 2 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100900 NV50_2D.DST_ADDRESS_LOW = 0x100900 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40088860 size 2, subchannel 4 (0x5c0000d3), offset 0x0860, constant +fffffffe NV50_2D.SIFC_DATA = 0xfffffffe +00000001 NV50_2D.SIFC_DATA = 0x1 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000032 NVA3_COMPUTE.QUERY_SEQUENCE = 0x32 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000188 201055c0 +# out of band: 0000018c 0000a600 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100800 NV50_2D.DST_ADDRESS_LOW = 0x100800 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000033 NVA3_COMPUTE.QUERY_SEQUENCE = 0x33 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000190 20105664 +# out of band: 00000194 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100700 NV50_2D.DST_ADDRESS_LOW = 0x100700 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000034 NVA3_COMPUTE.QUERY_SEQUENCE = 0x34 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000198 20105704 +# out of band: 0000019c 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100600 NV50_2D.DST_ADDRESS_LOW = 0x100600 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000035 NVA3_COMPUTE.QUERY_SEQUENCE = 0x35 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001a0 201057a4 +# out of band: 000001a4 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100500 NV50_2D.DST_ADDRESS_LOW = 0x100500 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000036 NVA3_COMPUTE.QUERY_SEQUENCE = 0x36 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001a8 20105844 +# out of band: 000001ac 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100400 NV50_2D.DST_ADDRESS_LOW = 0x100400 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000037 NVA3_COMPUTE.QUERY_SEQUENCE = 0x37 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001b0 201058e4 +# out of band: 000001b4 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100300 NV50_2D.DST_ADDRESS_LOW = 0x100300 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000038 NVA3_COMPUTE.QUERY_SEQUENCE = 0x38 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001b8 20105984 +# out of band: 000001bc 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100200 NV50_2D.DST_ADDRESS_LOW = 0x100200 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000039 NVA3_COMPUTE.QUERY_SEQUENCE = 0x39 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001c0 20105a24 +# out of band: 000001c4 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100100 NV50_2D.DST_ADDRESS_LOW = 0x100100 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000003a NVA3_COMPUTE.QUERY_SEQUENCE = 0x3a +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001c8 20105ac4 +# out of band: 000001cc 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00100000 NV50_2D.DST_ADDRESS_LOW = 0x100000 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000003b NVA3_COMPUTE.QUERY_SEQUENCE = 0x3b +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001d0 20105b64 +# out of band: 000001d4 0000a200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000014 NV50_2D.SIFC_WIDTH = 20 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2a00 NV50_2D.DST_ADDRESS_LOW = 0xfffc2a00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40508860 size 20, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004205 NV50_2D.SIFC_DATA = 0x10004205 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000005 NV50_2D.SIFC_DATA = 0xa0000005 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +60014c01 NV50_2D.SIFC_DATA = 0x60014c01 +00204780 NV50_2D.SIFC_DATA = 0x204780 +3000dc01 NV50_2D.SIFC_DATA = 0x3000dc01 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +307c01fd NV50_2D.SIFC_DATA = 0x307c01fd +6c0187c8 NV50_2D.SIFC_DATA = 0x6c0187c8 +3000d1fd NV50_2D.SIFC_DATA = 0x3000d1fd +6c2102c8 NV50_2D.SIFC_DATA = 0x6c2102c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +30020005 NV50_2D.SIFC_DATA = 0x30020005 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +1100ec00 NV50_2D.SIFC_DATA = 0x1100ec00 +2101e804 NV50_2D.SIFC_DATA = 0x2101e804 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000003c NVA3_COMPUTE.QUERY_SEQUENCE = 0x3c +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001d8 20105c04 +# out of band: 000001dc 0000ee00 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000003d NVA3_COMPUTE.QUERY_SEQUENCE = 0x3d +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001e0 20105cf0 +# out of band: 000001e4 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2800 NV50_2D.DST_ADDRESS_LOW = 0xfffc2800 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +41008860 size 64, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000009 NV50_2D.SIFC_DATA = 0xa0000009 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +60024c05 NV50_2D.SIFC_DATA = 0x60024c05 +00208780 NV50_2D.SIFC_DATA = 0x208780 +3000dc05 NV50_2D.SIFC_DATA = 0x3000dc05 +042047c0 NV50_2D.SIFC_DATA = 0x42047c0 +d0800205 NV50_2D.SIFC_DATA = 0xd0800205 +00400780 NV50_2D.SIFC_DATA = 0x400780 +3140f80d NV50_2D.SIFC_DATA = 0x3140f80d +04404780 NV50_2D.SIFC_DATA = 0x4404780 +10004401 NV50_2D.SIFC_DATA = 0x10004401 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000209 NV50_2D.SIFC_DATA = 0xa0000209 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +307c0215 NV50_2D.SIFC_DATA = 0x307c0215 +64018780 NV50_2D.SIFC_DATA = 0x64018780 +307c0611 NV50_2D.SIFC_DATA = 0x307c0611 +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +60004e01 NV50_2D.SIFC_DATA = 0x60004e01 +00208780 NV50_2D.SIFC_DATA = 0x208780 +d0050815 NV50_2D.SIFC_DATA = 0xd0050815 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +3001d021 NV50_2D.SIFC_DATA = 0x3001d021 +64210780 NV50_2D.SIFC_DATA = 0x64210780 +3003d209 NV50_2D.SIFC_DATA = 0x3003d209 +64208780 NV50_2D.SIFC_DATA = 0x64208780 +307cda1d NV50_2D.SIFC_DATA = 0x307cda1d +64208780 NV50_2D.SIFC_DATA = 0x64208780 +3000d819 NV50_2D.SIFC_DATA = 0x3000d819 +64210780 NV50_2D.SIFC_DATA = 0x64210780 +307c0611 NV50_2D.SIFC_DATA = 0x307c0611 +6c010780 NV50_2D.SIFC_DATA = 0x6c010780 +d0080409 NV50_2D.SIFC_DATA = 0xd0080409 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +3003d20d NV50_2D.SIFC_DATA = 0x3003d20d +64210780 NV50_2D.SIFC_DATA = 0x64210780 +d0060e19 NV50_2D.SIFC_DATA = 0xd0060e19 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0050815 NV50_2D.SIFC_DATA = 0xd0050815 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +307cda11 NV50_2D.SIFC_DATA = 0x307cda11 +64210780 NV50_2D.SIFC_DATA = 0x64210780 +d002060d NV50_2D.SIFC_DATA = 0xd002060d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d0060809 NV50_2D.SIFC_DATA = 0xd0060809 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d0030a0d NV50_2D.SIFC_DATA = 0xd0030a0d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d00305fd NV50_2D.SIFC_DATA = 0xd00305fd +040007c8 NV50_2D.SIFC_DATA = 0x40007c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +3002d409 NV50_2D.SIFC_DATA = 0x3002d409 +e4300780 NV50_2D.SIFC_DATA = 0xe4300780 +301ed60d NV50_2D.SIFC_DATA = 0x301ed60d +c4300780 NV50_2D.SIFC_DATA = 0xc4300780 +d0030409 NV50_2D.SIFC_DATA = 0xd0030409 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +a000f9fd NV50_2D.SIFC_DATA = 0xa000f9fd +040047c8 NV50_2D.SIFC_DATA = 0x40047c8 +1000f809 NV50_2D.SIFC_DATA = 0x1000f809 +0403c280 NV50_2D.SIFC_DATA = 0x403c280 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000010 NV50_2D.SIFC_WIDTH = 16 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2900 NV50_2D.DST_ADDRESS_LOW = 0xfffc2900 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40408860 size 16, subchannel 4 (0x5c0000d3), offset 0x0860, constant +4005000d NV50_2D.SIFC_DATA = 0x4005000d +00000780 NV50_2D.SIFC_DATA = 0x780 +6004020d NV50_2D.SIFC_DATA = 0x6004020d +0000c780 NV50_2D.SIFC_DATA = 0xc780 +3010060d NV50_2D.SIFC_DATA = 0x3010060d +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60040001 NV50_2D.SIFC_DATA = 0x60040001 +0000c780 NV50_2D.SIFC_DATA = 0xc780 +20000001 NV50_2D.SIFC_DATA = 0x20000001 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +30020005 NV50_2D.SIFC_DATA = 0x30020005 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +1100ec00 NV50_2D.SIFC_DATA = 0x1100ec00 +2101e804 NV50_2D.SIFC_DATA = 0x2101e804 +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000003e NVA3_COMPUTE.QUERY_SEQUENCE = 0x3e +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001e8 20105d0c +# out of band: 000001ec 00026600 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000003f NVA3_COMPUTE.QUERY_SEQUENCE = 0x3f +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001f0 20105f70 +# out of band: 000001f4 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000002 NV50_2D.SIFC_HEIGHT = 2 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000002 NV50_2D.DST_HEIGHT = 2 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2500 NV50_2D.DST_ADDRESS_LOW = 0xfffc2500 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +42008860 size 128, subchannel 4 (0x5c0000d3), offset 0x0860, constant +d0800209 NV50_2D.SIFC_DATA = 0xd0800209 +00400780 NV50_2D.SIFC_DATA = 0x400780 +10004405 NV50_2D.SIFC_DATA = 0x10004405 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000409 NV50_2D.SIFC_DATA = 0xa0000409 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a000000d NV50_2D.SIFC_DATA = 0xa000000d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +60014e15 NV50_2D.SIFC_DATA = 0x60014e15 +00208780 NV50_2D.SIFC_DATA = 0x208780 +307cdbfd NV50_2D.SIFC_DATA = 0x307cdbfd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +60024c01 NV50_2D.SIFC_DATA = 0x60024c01 +0020c780 NV50_2D.SIFC_DATA = 0x20c780 +3005d9fd NV50_2D.SIFC_DATA = 0x3005d9fd +6420c2c8 NV50_2D.SIFC_DATA = 0x6420c2c8 +3000dc01 NV50_2D.SIFC_DATA = 0x3000dc01 +042007d0 NV50_2D.SIFC_DATA = 0x42007d0 +1000d009 NV50_2D.SIFC_DATA = 0x1000d009 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +307cdbfd NV50_2D.SIFC_DATA = 0x307cdbfd +64204148 NV50_2D.SIFC_DATA = 0x64204148 +1100f20c NV50_2D.SIFC_DATA = 0x1100f20c +10008018 NV50_2D.SIFC_DATA = 0x10008018 +3140f805 NV50_2D.SIFC_DATA = 0x3140f805 +04405780 NV50_2D.SIFC_DATA = 0x4405780 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000280 NV50_2D.SIFC_DATA = 0x280 +3001d411 NV50_2D.SIFC_DATA = 0x3001d411 +e4300780 NV50_2D.SIFC_DATA = 0xe4300780 +301fd61d NV50_2D.SIFC_DATA = 0x301fd61d +c4300780 NV50_2D.SIFC_DATA = 0xc4300780 +d0070811 NV50_2D.SIFC_DATA = 0xd0070811 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +a000f9fd NV50_2D.SIFC_DATA = 0xa000f9fd +040047c8 NV50_2D.SIFC_DATA = 0x40047c8 +1000f811 NV50_2D.SIFC_DATA = 0x1000f811 +0403c280 NV50_2D.SIFC_DATA = 0x403c280 +400b101d NV50_2D.SIFC_DATA = 0x400b101d +00000780 NV50_2D.SIFC_DATA = 0x780 +600a121d NV50_2D.SIFC_DATA = 0x600a121d +0001c780 NV50_2D.SIFC_DATA = 0x1c780 +30100e1d NV50_2D.SIFC_DATA = 0x30100e1d +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +600a1011 NV50_2D.SIFC_DATA = 0x600a1011 +0001c780 NV50_2D.SIFC_DATA = 0x1c780 +30010811 NV50_2D.SIFC_DATA = 0x30010811 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +2000c815 NV50_2D.SIFC_DATA = 0x2000c815 +04210780 NV50_2D.SIFC_DATA = 0x4210780 +d0820bfd NV50_2D.SIFC_DATA = 0xd0820bfd +044007c8 NV50_2D.SIFC_DATA = 0x44007c8 +10000a11 NV50_2D.SIFC_DATA = 0x10000a11 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +104c7003 NV50_2D.SIFC_DATA = 0x104c7003 +00000100 NV50_2D.SIFC_DATA = 0x100 +308101fd NV50_2D.SIFC_DATA = 0x308101fd +644087c8 NV50_2D.SIFC_DATA = 0x644087c8 +308103fd NV50_2D.SIFC_DATA = 0x308103fd +6c4082c8 NV50_2D.SIFC_DATA = 0x6c4082c8 +1000cc11 NV50_2D.SIFC_DATA = 0x1000cc11 +0423c680 NV50_2D.SIFC_DATA = 0x423c680 +d00e0a11 NV50_2D.SIFC_DATA = 0xd00e0a11 +a0600680 NV50_2D.SIFC_DATA = 0xa0600680 +21400409 NV50_2D.SIFC_DATA = 0x21400409 +0440c7d0 NV50_2D.SIFC_DATA = 0x440c7d0 +307c05fd NV50_2D.SIFC_DATA = 0x307c05fd +640087c8 NV50_2D.SIFC_DATA = 0x640087c8 +3140060d NV50_2D.SIFC_DATA = 0x3140060d +04405780 NV50_2D.SIFC_DATA = 0x4405780 +307c07fd NV50_2D.SIFC_DATA = 0x307c07fd +640082c8 NV50_2D.SIFC_DATA = 0x640082c8 +20028a11 NV50_2D.SIFC_DATA = 0x20028a11 +00000003 NV50_2D.SIFC_DATA = 0x3 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000680 NV50_2D.SIFC_DATA = 0x680 +21400421 NV50_2D.SIFC_DATA = 0x21400421 +0440c7d0 NV50_2D.SIFC_DATA = 0x440c7d0 +2000001d NV50_2D.SIFC_DATA = 0x2000001d +040007c0 NV50_2D.SIFC_DATA = 0x40007c0 +307c0215 NV50_2D.SIFC_DATA = 0x307c0215 +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +3140060d NV50_2D.SIFC_DATA = 0x3140060d +04405780 NV50_2D.SIFC_DATA = 0x4405780 +30400225 NV50_2D.SIFC_DATA = 0x30400225 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +307c0029 NV50_2D.SIFC_DATA = 0x307c0029 +64018780 NV50_2D.SIFC_DATA = 0x64018780 +30080e21 NV50_2D.SIFC_DATA = 0x30080e21 +64004780 NV50_2D.SIFC_DATA = 0x64004780 +3003121d NV50_2D.SIFC_DATA = 0x3003121d +64008780 NV50_2D.SIFC_DATA = 0x64008780 +d00a0a15 NV50_2D.SIFC_DATA = 0xd00a0a15 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +3003120d NV50_2D.SIFC_DATA = 0x3003120d +64004780 NV50_2D.SIFC_DATA = 0x64004780 +307c0225 NV50_2D.SIFC_DATA = 0x307c0225 +6c010780 NV50_2D.SIFC_DATA = 0x6c010780 +d0080e1d NV50_2D.SIFC_DATA = 0xd0080e1d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0051215 NV50_2D.SIFC_DATA = 0xd0051215 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d007060d NV50_2D.SIFC_DATA = 0xd007060d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d0030bfd NV50_2D.SIFC_DATA = 0xd0030bfd +040007c8 NV50_2D.SIFC_DATA = 0x40007c8 +d084cc15 NV50_2D.SIFC_DATA = 0xd084cc15 +04600680 NV50_2D.SIFC_DATA = 0x4600680 +3010cc1d NV50_2D.SIFC_DATA = 0x3010cc1d +c4300680 NV50_2D.SIFC_DATA = 0xc4300680 +30020c0d NV50_2D.SIFC_DATA = 0x30020c0d +c4100680 NV50_2D.SIFC_DATA = 0xc4100680 +d0070a15 NV50_2D.SIFC_DATA = 0xd0070a15 +04004680 NV50_2D.SIFC_DATA = 0x4004680 +2000080d NV50_2D.SIFC_DATA = 0x2000080d +0400c680 NV50_2D.SIFC_DATA = 0x400c680 +d00e0615 NV50_2D.SIFC_DATA = 0xd00e0615 +a0c00680 NV50_2D.SIFC_DATA = 0xa0c00680 +30010409 NV50_2D.SIFC_DATA = 0x30010409 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +20000409 NV50_2D.SIFC_DATA = 0x20000409 +04010780 NV50_2D.SIFC_DATA = 0x4010780 +d082040d NV50_2D.SIFC_DATA = 0xd082040d +04400780 NV50_2D.SIFC_DATA = 0x4400780 +307c0205 NV50_2D.SIFC_DATA = 0x307c0205 +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000012 NV50_2D.SIFC_WIDTH = 18 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2700 NV50_2D.DST_ADDRESS_LOW = 0xfffc2700 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40488860 size 18, subchannel 4 (0x5c0000d3), offset 0x0860, constant +307c0001 NV50_2D.SIFC_DATA = 0x307c0001 +64008780 NV50_2D.SIFC_DATA = 0x64008780 +307c060d NV50_2D.SIFC_DATA = 0x307c060d +64008780 NV50_2D.SIFC_DATA = 0x64008780 +d0010001 NV50_2D.SIFC_DATA = 0xd0010001 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d0030005 NV50_2D.SIFC_DATA = 0xd0030005 +0402c780 NV50_2D.SIFC_DATA = 0x402c780 +d00101fd NV50_2D.SIFC_DATA = 0xd00101fd +040007c8 NV50_2D.SIFC_DATA = 0x40007c8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000100 NV50_2D.SIFC_DATA = 0x100 +1000cc01 NV50_2D.SIFC_DATA = 0x1000cc01 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +203e8405 NV50_2D.SIFC_DATA = 0x203e8405 +0fffffff NV50_2D.SIFC_DATA = 0xfffffff +d00e0201 NV50_2D.SIFC_DATA = 0xd00e0201 +a0600781 NV50_2D.SIFC_DATA = 0xa0600781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000040 NVA3_COMPUTE.QUERY_SEQUENCE = 0x40 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 000001f8 20105f8c +# out of band: 000001fc 00036e00 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000041 NVA3_COMPUTE.QUERY_SEQUENCE = 0x41 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000200 201062f8 +# out of band: 00000204 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000002 NV50_2D.SIFC_HEIGHT = 2 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000002 NV50_2D.DST_HEIGHT = 2 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2200 NV50_2D.DST_ADDRESS_LOW = 0xfffc2200 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +42008860 size 128, subchannel 4 (0x5c0000d3), offset 0x0860, constant +d0800209 NV50_2D.SIFC_DATA = 0xd0800209 +00400780 NV50_2D.SIFC_DATA = 0x400780 +10004405 NV50_2D.SIFC_DATA = 0x10004405 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000409 NV50_2D.SIFC_DATA = 0xa0000409 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +10004209 NV50_2D.SIFC_DATA = 0x10004209 +0023c780 NV50_2D.SIFC_DATA = 0x23c780 +a0000011 NV50_2D.SIFC_DATA = 0xa0000011 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +60014e0d NV50_2D.SIFC_DATA = 0x60014e0d +00208780 NV50_2D.SIFC_DATA = 0x208780 +307cdbfd NV50_2D.SIFC_DATA = 0x307cdbfd +642087c8 NV50_2D.SIFC_DATA = 0x642087c8 +60024c01 NV50_2D.SIFC_DATA = 0x60024c01 +00210780 NV50_2D.SIFC_DATA = 0x210780 +3003d9fd NV50_2D.SIFC_DATA = 0x3003d9fd +6420c2c8 NV50_2D.SIFC_DATA = 0x6420c2c8 +3000dc01 NV50_2D.SIFC_DATA = 0x3000dc01 +042007d0 NV50_2D.SIFC_DATA = 0x42007d0 +307cdbfd NV50_2D.SIFC_DATA = 0x307cdbfd +64204148 NV50_2D.SIFC_DATA = 0x64204148 +10000011 NV50_2D.SIFC_DATA = 0x10000011 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +3140f805 NV50_2D.SIFC_DATA = 0x3140f805 +04405780 NV50_2D.SIFC_DATA = 0x4405780 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00000280 NV50_2D.SIFC_DATA = 0x280 +1000d409 NV50_2D.SIFC_DATA = 0x1000d409 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +40070815 NV50_2D.SIFC_DATA = 0x40070815 +00000780 NV50_2D.SIFC_DATA = 0x780 +60060a15 NV50_2D.SIFC_DATA = 0x60060a15 +00014780 NV50_2D.SIFC_DATA = 0x14780 +30100a15 NV50_2D.SIFC_DATA = 0x30100a15 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60060809 NV50_2D.SIFC_DATA = 0x60060809 +00014780 NV50_2D.SIFC_DATA = 0x14780 +2000c815 NV50_2D.SIFC_DATA = 0x2000c815 +04208780 NV50_2D.SIFC_DATA = 0x4208780 +d0820a09 NV50_2D.SIFC_DATA = 0xd0820a09 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +30048419 NV50_2D.SIFC_DATA = 0x30048419 +00000003 NV50_2D.SIFC_DATA = 0x3 +307c0009 NV50_2D.SIFC_DATA = 0x307c0009 +64008780 NV50_2D.SIFC_DATA = 0x64008780 +307c020d NV50_2D.SIFC_DATA = 0x307c020d +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +307cd3fd NV50_2D.SIFC_DATA = 0x307cd3fd +642087d8 NV50_2D.SIFC_DATA = 0x642087d8 +d0820c19 NV50_2D.SIFC_DATA = 0xd0820c19 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +d0030409 NV50_2D.SIFC_DATA = 0xd0030409 +040007e0 NV50_2D.SIFC_DATA = 0x40007e0 +3006d1fd NV50_2D.SIFC_DATA = 0x3006d1fd +6420d2d8 NV50_2D.SIFC_DATA = 0x6420d2d8 +a00005fd NV50_2D.SIFC_DATA = 0xa00005fd +0c0147c8 NV50_2D.SIFC_DATA = 0xc0147c8 +a046b003 NV50_2D.SIFC_DATA = 0xa046b003 +00000000 NV50_2D.SIFC_DATA = 0 +307cd3fd NV50_2D.SIFC_DATA = 0x307cd3fd +64205158 NV50_2D.SIFC_DATA = 0x64205158 +1000d019 NV50_2D.SIFC_DATA = 0x1000d019 +0423d280 NV50_2D.SIFC_DATA = 0x423d280 +1046b003 NV50_2D.SIFC_DATA = 0x1046b003 +00002100 NV50_2D.SIFC_DATA = 0x2100 +307c0dfd NV50_2D.SIFC_DATA = 0x307c0dfd +640087d8 NV50_2D.SIFC_DATA = 0x640087d8 +1046b003 NV50_2D.SIFC_DATA = 0x1046b003 +00001280 NV50_2D.SIFC_DATA = 0x1280 +10000a0d NV50_2D.SIFC_DATA = 0x10000a0d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1000f81d NV50_2D.SIFC_DATA = 0x1000f81d +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +1000cc09 NV50_2D.SIFC_DATA = 0x1000cc09 +0423c780 NV50_2D.SIFC_DATA = 0x423c780 +20018e1d NV50_2D.SIFC_DATA = 0x20018e1d +00000003 NV50_2D.SIFC_DATA = 0x3 +d00e0609 NV50_2D.SIFC_DATA = 0xd00e0609 +a0200780 NV50_2D.SIFC_DATA = 0xa0200780 +30060ffd NV50_2D.SIFC_DATA = 0x30060ffd +640147d8 NV50_2D.SIFC_DATA = 0x640147d8 +2001860d NV50_2D.SIFC_DATA = 0x2001860d +00000003 NV50_2D.SIFC_DATA = 0x3 +10465003 NV50_2D.SIFC_DATA = 0x10465003 +00001280 NV50_2D.SIFC_DATA = 0x1280 +2040d009 NV50_2D.SIFC_DATA = 0x2040d009 +042187e2 NV50_2D.SIFC_DATA = 0x42187e2 +307c05fd NV50_2D.SIFC_DATA = 0x307c05fd +640087d8 NV50_2D.SIFC_DATA = 0x640087d8 +3140d20d NV50_2D.SIFC_DATA = 0x3140d20d +04606780 NV50_2D.SIFC_DATA = 0x4606780 +307c07fd NV50_2D.SIFC_DATA = 0x307c07fd +640092d8 NV50_2D.SIFC_DATA = 0x640092d8 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00001680 NV50_2D.SIFC_DATA = 0x1680 +30020221 NV50_2D.SIFC_DATA = 0x30020221 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +1020801d NV50_2D.SIFC_DATA = 0x1020801d +00000003 NV50_2D.SIFC_DATA = 0x3 +301e0025 NV50_2D.SIFC_DATA = 0x301e0025 +e4100780 NV50_2D.SIFC_DATA = 0xe4100780 +21000ffd NV50_2D.SIFC_DATA = 0x21000ffd +044107d8 NV50_2D.SIFC_DATA = 0x44107d8 +d009101d NV50_2D.SIFC_DATA = 0xd009101d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +307c0221 NV50_2D.SIFC_DATA = 0x307c0221 +6c008780 NV50_2D.SIFC_DATA = 0x6c008780 +30020025 NV50_2D.SIFC_DATA = 0x30020025 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +d0830429 NV50_2D.SIFC_DATA = 0xd0830429 +04400780 NV50_2D.SIFC_DATA = 0x4400780 +1000f81d NV50_2D.SIFC_DATA = 0x1000f81d +0403d980 NV50_2D.SIFC_DATA = 0x403d980 +307c0001 NV50_2D.SIFC_DATA = 0x307c0001 +64018780 NV50_2D.SIFC_DATA = 0x64018780 +300a1229 NV50_2D.SIFC_DATA = 0x300a1229 +64004780 NV50_2D.SIFC_DATA = 0x64004780 +30030e25 NV50_2D.SIFC_DATA = 0x30030e25 +64008780 NV50_2D.SIFC_DATA = 0x64008780 +d0001001 NV50_2D.SIFC_DATA = 0xd0001001 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +30030e0d NV50_2D.SIFC_DATA = 0x30030e0d +64004780 NV50_2D.SIFC_DATA = 0x64004780 +307c0205 NV50_2D.SIFC_DATA = 0x307c0205 +6c010780 NV50_2D.SIFC_DATA = 0x6c010780 +d00a121d NV50_2D.SIFC_DATA = 0xd00a121d +04000780 NV50_2D.SIFC_DATA = 0x4000780 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000038 NV50_2D.SIFC_WIDTH = 56 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2400 NV50_2D.DST_ADDRESS_LOW = 0xfffc2400 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40e08860 size 56, subchannel 4 (0x5c0000d3), offset 0x0860, constant +d0000201 NV50_2D.SIFC_DATA = 0xd0000201 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d0070605 NV50_2D.SIFC_DATA = 0xd0070605 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d00101fd NV50_2D.SIFC_DATA = 0xd00101fd +040007d8 NV50_2D.SIFC_DATA = 0x40007d8 +a048e003 NV50_2D.SIFC_DATA = 0xa048e003 +00000000 NV50_2D.SIFC_DATA = 0 +1048e003 NV50_2D.SIFC_DATA = 0x1048e003 +00001100 NV50_2D.SIFC_DATA = 0x1100 +d085cc01 NV50_2D.SIFC_DATA = 0xd085cc01 +04600780 NV50_2D.SIFC_DATA = 0x4600780 +30080005 NV50_2D.SIFC_DATA = 0x30080005 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +d000020d NV50_2D.SIFC_DATA = 0xd000020d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +30020805 NV50_2D.SIFC_DATA = 0x30020805 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +30100611 NV50_2D.SIFC_DATA = 0x30100611 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +20000c01 NV50_2D.SIFC_DATA = 0x20000c01 +04014780 NV50_2D.SIFC_DATA = 0x4014780 +d004060d NV50_2D.SIFC_DATA = 0xd004060d +04004780 NV50_2D.SIFC_DATA = 0x4004780 +20000001 NV50_2D.SIFC_DATA = 0x20000001 +04004780 NV50_2D.SIFC_DATA = 0x4004780 +d00e000d NV50_2D.SIFC_DATA = 0xd00e000d +a0c00780 NV50_2D.SIFC_DATA = 0xa0c00780 +2000d001 NV50_2D.SIFC_DATA = 0x2000d001 +04214782 NV50_2D.SIFC_DATA = 0x4214782 +d0820005 NV50_2D.SIFC_DATA = 0xd0820005 +044007d0 NV50_2D.SIFC_DATA = 0x44007d0 +30000003 NV50_2D.SIFC_DATA = 0x30000003 +00001100 NV50_2D.SIFC_DATA = 0x1100 +20000c0d NV50_2D.SIFC_DATA = 0x20000c0d +04014780 NV50_2D.SIFC_DATA = 0x4014780 +1000f811 NV50_2D.SIFC_DATA = 0x1000f811 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +20400415 NV50_2D.SIFC_DATA = 0x20400415 +04010680 NV50_2D.SIFC_DATA = 0x4010680 +1000cc01 NV50_2D.SIFC_DATA = 0x1000cc01 +0423c680 NV50_2D.SIFC_DATA = 0x423c680 +20000615 NV50_2D.SIFC_DATA = 0x20000615 +04014680 NV50_2D.SIFC_DATA = 0x4014680 +21000a15 NV50_2D.SIFC_DATA = 0x21000a15 +04418680 NV50_2D.SIFC_DATA = 0x4418680 +d00e0a01 NV50_2D.SIFC_DATA = 0xd00e0a01 +a0200680 NV50_2D.SIFC_DATA = 0xa0200680 +20018811 NV50_2D.SIFC_DATA = 0x20018811 +00000003 NV50_2D.SIFC_DATA = 0x3 +300109fd NV50_2D.SIFC_DATA = 0x300109fd +640147d8 NV50_2D.SIFC_DATA = 0x640147d8 +10493003 NV50_2D.SIFC_DATA = 0x10493003 +00001280 NV50_2D.SIFC_DATA = 0x1280 +f0000001 NV50_2D.SIFC_DATA = 0xf0000001 +e0000001 NV50_2D.SIFC_DATA = 0xe0000001 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000042 NVA3_COMPUTE.QUERY_SEQUENCE = 0x42 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000208 20106314 +# out of band: 0000020c 00040600 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000043 NVA3_COMPUTE.QUERY_SEQUENCE = 0x43 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000210 20106718 +# out of band: 00000214 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000002 NV50_2D.SIFC_WIDTH = 2 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00101400 NV50_2D.DST_ADDRESS_LOW = 0x101400 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40088860 size 2, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +ffffffff NV50_2D.SIFC_DATA = 0xffffffff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000044 NVA3_COMPUTE.QUERY_SEQUENCE = 0x44 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000218 20106734 +# out of band: 0000021c 0000a600 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000005 NV50_2D.SIFC_WIDTH = 5 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00101300 NV50_2D.DST_ADDRESS_LOW = 0x101300 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40148860 size 5, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +ffffffff NV50_2D.SIFC_DATA = 0xffffffff +00000002 NV50_2D.SIFC_DATA = 0x2 +00000001 NV50_2D.SIFC_DATA = 0x1 +0000ffff NV50_2D.SIFC_DATA = 0xffff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000045 NVA3_COMPUTE.QUERY_SEQUENCE = 0x45 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000220 201067d8 +# out of band: 00000224 0000b200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000008 NV50_2D.SIFC_WIDTH = 8 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00101200 NV50_2D.DST_ADDRESS_LOW = 0x101200 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40208860 size 8, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000003ff NV50_2D.SIFC_DATA = 0x3ff +ffffffff NV50_2D.SIFC_DATA = 0xffffffff +00000003 NV50_2D.SIFC_DATA = 0x3 +fffffffc NV50_2D.SIFC_DATA = 0xfffffffc +fffffffe NV50_2D.SIFC_DATA = 0xfffffffe +000000ff NV50_2D.SIFC_DATA = 0xff +ffffffff NV50_2D.SIFC_DATA = 0xffffffff +ffffffff NV50_2D.SIFC_DATA = 0xffffffff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000046 NVA3_COMPUTE.QUERY_SEQUENCE = 0x46 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000228 20106888 +# out of band: 0000022c 0000be00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000002 NV50_2D.SIFC_WIDTH = 2 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2b00 NV50_2D.DST_ADDRESS_LOW = 0xfffc2b00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40088860 size 2, subchannel 4 (0x5c0000d3), offset 0x0860, constant +f0000001 NV50_2D.SIFC_DATA = 0xf0000001 +e0000001 NV50_2D.SIFC_DATA = 0xe0000001 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000047 NVA3_COMPUTE.QUERY_SEQUENCE = 0x47 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000230 20106944 +# out of band: 00000234 0000a600 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000048 NVA3_COMPUTE.QUERY_SEQUENCE = 0x48 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000238 201069e8 +# out of band: 0000023c 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2e00 NV50_2D.DST_ADDRESS_LOW = 0xfffc2e00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +41008860 size 64, subchannel 4 (0x5c0000d3), offset 0x0860, constant +41032c05 NV50_2D.SIFC_DATA = 0x41032c05 +00000003 NV50_2D.SIFC_DATA = 0x3 +a0000001 NV50_2D.SIFC_DATA = 0xa0000001 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +30020209 NV50_2D.SIFC_DATA = 0x30020209 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +3002000d NV50_2D.SIFC_DATA = 0x3002000d +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +2102e810 NV50_2D.SIFC_DATA = 0x2102e810 +2103ec18 NV50_2D.SIFC_DATA = 0x2103ec18 +20000205 NV50_2D.SIFC_DATA = 0x20000205 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +20048801 NV50_2D.SIFC_DATA = 0x20048801 +00000003 NV50_2D.SIFC_DATA = 0x3 +d00e080d NV50_2D.SIFC_DATA = 0xd00e080d +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d00e0c09 NV50_2D.SIFC_DATA = 0xd00e0c09 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d00e0001 NV50_2D.SIFC_DATA = 0xd00e0001 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +40070815 NV50_2D.SIFC_DATA = 0x40070815 +00000780 NV50_2D.SIFC_DATA = 0x780 +60060a15 NV50_2D.SIFC_DATA = 0x60060a15 +00014780 NV50_2D.SIFC_DATA = 0x14780 +30100a15 NV50_2D.SIFC_DATA = 0x30100a15 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60060815 NV50_2D.SIFC_DATA = 0x60060815 +00014780 NV50_2D.SIFC_DATA = 0x14780 +20088809 NV50_2D.SIFC_DATA = 0x20088809 +00000003 NV50_2D.SIFC_DATA = 0x3 +200c8c0d NV50_2D.SIFC_DATA = 0x200c8c0d +00000003 NV50_2D.SIFC_DATA = 0x3 +20188c19 NV50_2D.SIFC_DATA = 0x20188c19 +00000003 NV50_2D.SIFC_DATA = 0x3 +d00e0409 NV50_2D.SIFC_DATA = 0xd00e0409 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d00e0611 NV50_2D.SIFC_DATA = 0xd00e0611 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d00e0c0d NV50_2D.SIFC_DATA = 0xd00e0c0d +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +40090019 NV50_2D.SIFC_DATA = 0x40090019 +00000780 NV50_2D.SIFC_DATA = 0x780 +60080219 NV50_2D.SIFC_DATA = 0x60080219 +00018780 NV50_2D.SIFC_DATA = 0x18780 +4007081d NV50_2D.SIFC_DATA = 0x4007081d +00000780 NV50_2D.SIFC_DATA = 0x780 +30100c19 NV50_2D.SIFC_DATA = 0x30100c19 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60060a1d NV50_2D.SIFC_DATA = 0x60060a1d +0001c780 NV50_2D.SIFC_DATA = 0x1c780 +60080001 NV50_2D.SIFC_DATA = 0x60080001 +00018780 NV50_2D.SIFC_DATA = 0x18780 +30100e19 NV50_2D.SIFC_DATA = 0x30100e19 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +20000a11 NV50_2D.SIFC_DATA = 0x20000a11 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +60060809 NV50_2D.SIFC_DATA = 0x60060809 +00018780 NV50_2D.SIFC_DATA = 0x18780 +30020201 NV50_2D.SIFC_DATA = 0x30020201 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +20048404 NV50_2D.SIFC_DATA = 0x20048404 +2100f000 NV50_2D.SIFC_DATA = 0x2100f000 +d00e0005 NV50_2D.SIFC_DATA = 0xd00e0005 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000049 NVA3_COMPUTE.QUERY_SEQUENCE = 0x49 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000240 20106a04 +# out of band: 00000244 00019e00 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000004a NVA3_COMPUTE.QUERY_SEQUENCE = 0x4a +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000248 20106ba0 +# out of band: 0000024c 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000040 NV50_2D.SIFC_WIDTH = 64 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2c00 NV50_2D.DST_ADDRESS_LOW = 0xfffc2c00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +41008860 size 64, subchannel 4 (0x5c0000d3), offset 0x0860, constant +10001405 NV50_2D.SIFC_DATA = 0x10001405 +4400c780 NV50_2D.SIFC_DATA = 0x4400c780 +a0000001 NV50_2D.SIFC_DATA = 0xa0000001 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +d00e0211 NV50_2D.SIFC_DATA = 0xd00e0211 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +307c09fd NV50_2D.SIFC_DATA = 0x307c09fd +640087c8 NV50_2D.SIFC_DATA = 0x640087c8 +a0004c05 NV50_2D.SIFC_DATA = 0xa0004c05 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +1059b003 NV50_2D.SIFC_DATA = 0x1059b003 +00000280 NV50_2D.SIFC_DATA = 0x280 +40031009 NV50_2D.SIFC_DATA = 0x40031009 +00000780 NV50_2D.SIFC_DATA = 0x780 +60021209 NV50_2D.SIFC_DATA = 0x60021209 +00008780 NV50_2D.SIFC_DATA = 0x8780 +30100409 NV50_2D.SIFC_DATA = 0x30100409 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60021009 NV50_2D.SIFC_DATA = 0x60021009 +00008780 NV50_2D.SIFC_DATA = 0x8780 +1000000d NV50_2D.SIFC_DATA = 0x1000000d +0603c780 NV50_2D.SIFC_DATA = 0x603c780 +1000f821 NV50_2D.SIFC_DATA = 0x1000f821 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +10028404 NV50_2D.SIFC_DATA = 0x10028404 +2004841c NV50_2D.SIFC_DATA = 0x2004841c +30020619 NV50_2D.SIFC_DATA = 0x30020619 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +30020415 NV50_2D.SIFC_DATA = 0x30020415 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +2106ec24 NV50_2D.SIFC_DATA = 0x2106ec24 +2105e818 NV50_2D.SIFC_DATA = 0x2105e818 +d00e1215 NV50_2D.SIFC_DATA = 0xd00e1215 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +d00e0c19 NV50_2D.SIFC_DATA = 0xd00e0c19 +80c00780 NV50_2D.SIFC_DATA = 0x80c00780 +400d1425 NV50_2D.SIFC_DATA = 0x400d1425 +00000780 NV50_2D.SIFC_DATA = 0x780 +600c1625 NV50_2D.SIFC_DATA = 0x600c1625 +00024780 NV50_2D.SIFC_DATA = 0x24780 +30101225 NV50_2D.SIFC_DATA = 0x30101225 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +20018409 NV50_2D.SIFC_DATA = 0x20018409 +00000003 NV50_2D.SIFC_DATA = 0x3 +600c1415 NV50_2D.SIFC_DATA = 0x600c1415 +00024780 NV50_2D.SIFC_DATA = 0x24780 +300705fd NV50_2D.SIFC_DATA = 0x300705fd +640147c8 NV50_2D.SIFC_DATA = 0x640147c8 +20088a20 NV50_2D.SIFC_DATA = 0x20088a20 +2004860c NV50_2D.SIFC_DATA = 0x2004860c +1058d003 NV50_2D.SIFC_DATA = 0x1058d003 +00000280 NV50_2D.SIFC_DATA = 0x280 +105a0003 NV50_2D.SIFC_DATA = 0x105a0003 +00000780 NV50_2D.SIFC_DATA = 0x780 +40031009 NV50_2D.SIFC_DATA = 0x40031009 +00000780 NV50_2D.SIFC_DATA = 0x780 +60021209 NV50_2D.SIFC_DATA = 0x60021209 +00008780 NV50_2D.SIFC_DATA = 0x8780 +30100409 NV50_2D.SIFC_DATA = 0x30100409 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +60021005 NV50_2D.SIFC_DATA = 0x60021005 +00008780 NV50_2D.SIFC_DATA = 0x8780 +1000f821 NV50_2D.SIFC_DATA = 0x1000f821 +0403c780 NV50_2D.SIFC_DATA = 0x403c780 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000008 NV50_2D.SIFC_WIDTH = 8 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000fd NV50_2D.DST_ADDRESS_HIGH = 0xfd +fffc2d00 NV50_2D.DST_ADDRESS_LOW = 0xfffc2d00 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40208860 size 8, subchannel 4 (0x5c0000d3), offset 0x0860, constant +20000201 NV50_2D.SIFC_DATA = 0x20000201 +04000780 NV50_2D.SIFC_DATA = 0x4000780 +30020001 NV50_2D.SIFC_DATA = 0x30020001 +c4100780 NV50_2D.SIFC_DATA = 0xc4100780 +2000d001 NV50_2D.SIFC_DATA = 0x2000d001 +04200780 NV50_2D.SIFC_DATA = 0x4200780 +d00e0021 NV50_2D.SIFC_DATA = 0xd00e0021 +a0c00781 NV50_2D.SIFC_DATA = 0xa0c00781 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000004b NVA3_COMPUTE.QUERY_SEQUENCE = 0x4b +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000250 20106bbc +# out of band: 00000254 00024600 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000004c NVA3_COMPUTE.QUERY_SEQUENCE = 0x4c +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000258 20106e00 +# out of band: 0000025c 00001e00 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000009 NV50_2D.SIFC_WIDTH = 9 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00200000 NV50_2D.DST_ADDRESS_LOW = 0x200000 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40248860 size 9, subchannel 4 (0x5c0000d3), offset 0x0860, constant +00000000 NV50_2D.SIFC_DATA = 0 +00000001 NV50_2D.SIFC_DATA = 0x1 +00000002 NV50_2D.SIFC_DATA = 0x2 +00000003 NV50_2D.SIFC_DATA = 0x3 +00000004 NV50_2D.SIFC_DATA = 0x4 +00000005 NV50_2D.SIFC_DATA = 0x5 +00000006 NV50_2D.SIFC_DATA = 0x6 +00000007 NV50_2D.SIFC_DATA = 0x7 +00000008 NV50_2D.SIFC_DATA = 0x8 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000004d NVA3_COMPUTE.QUERY_SEQUENCE = 0x4d +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000260 20106e1c +# out of band: 00000264 0000c200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000009 NV50_2D.SIFC_WIDTH = 9 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00200100 NV50_2D.DST_ADDRESS_LOW = 0x200100 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40248860 size 9, subchannel 4 (0x5c0000d3), offset 0x0860, constant +00000002 NV50_2D.SIFC_DATA = 0x2 +00000000 NV50_2D.SIFC_DATA = 0 +00000000 NV50_2D.SIFC_DATA = 0 +00000000 NV50_2D.SIFC_DATA = 0 +00000002 NV50_2D.SIFC_DATA = 0x2 +00000000 NV50_2D.SIFC_DATA = 0 +00000000 NV50_2D.SIFC_DATA = 0 +00000000 NV50_2D.SIFC_DATA = 0 +00000002 NV50_2D.SIFC_DATA = 0x2 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000004e NVA3_COMPUTE.QUERY_SEQUENCE = 0x4e +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000268 20106edc +# out of band: 0000026c 0000c200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000009 NV50_2D.SIFC_WIDTH = 9 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00200200 NV50_2D.DST_ADDRESS_LOW = 0x200200 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40248860 size 9, subchannel 4 (0x5c0000d3), offset 0x0860, constant +000000ff NV50_2D.SIFC_DATA = 0xff +000000ff NV50_2D.SIFC_DATA = 0xff +000000ff NV50_2D.SIFC_DATA = 0xff +000000ff NV50_2D.SIFC_DATA = 0xff +000000ff NV50_2D.SIFC_DATA = 0xff +000000ff NV50_2D.SIFC_DATA = 0xff +000000ff NV50_2D.SIFC_DATA = 0xff +000000ff NV50_2D.SIFC_DATA = 0xff +000000ff NV50_2D.SIFC_DATA = 0xff +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +0000004f NVA3_COMPUTE.QUERY_SEQUENCE = 0x4f +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000270 20106f9c +# out of band: 00000274 0000c200 +00048290 size 1, subchannel 4 (0x5c0000d3), offset 0x0290, increment +00000000 NV50_2D.CLIP_ENABLE = FALSE +0004829c size 1, subchannel 4 (0x5c0000d3), offset 0x029c, increment +00000000 NV50_2D.COLOR_KEY_ENABLE = FALSE +000482ac size 1, subchannel 4 (0x5c0000d3), offset 0x02ac, increment +00000003 NV50_2D.OPERATION = SRCCOPY +00088838 size 2, subchannel 4 (0x5c0000d3), offset 0x0838, increment +00000001 NV50_2D.SIFC_WIDTH = 1 +00000001 NV50_2D.SIFC_HEIGHT = 1 +00208200 size 8, subchannel 4 (0x5c0000d3), offset 0x0200, increment +000000ff NV50_2D.DST_FORMAT = Y32_UINT_UNKFF +00000001 NV50_2D.DST_LINEAR = TRUE +00000000 NV50_2D.DST_TILE_MODE = 0 +00000001 NV50_2D.DST_DEPTH = 1 +00000000 NV50_2D.DST_LAYER = 0 +00000100 NV50_2D.DST_PITCH = 256 +00000040 NV50_2D.DST_WIDTH = 64 +00000001 NV50_2D.DST_HEIGHT = 1 +00088220 size 2, subchannel 4 (0x5c0000d3), offset 0x0220, increment +000000ff NV50_2D.DST_ADDRESS_HIGH = 0xff +00200300 NV50_2D.DST_ADDRESS_LOW = 0x200300 +00088800 size 2, subchannel 4 (0x5c0000d3), offset 0x0800, increment +00000000 NV50_2D.SIFC_BITMAP_ENABLE = FALSE +000000ff NV50_2D.SIFC_FORMAT = Y32_UINT_UNKFF +00208840 size 8, subchannel 4 (0x5c0000d3), offset 0x0840, increment +00000000 NV50_2D.SIFC_DX_DU_FRACT = 0 +00000001 NV50_2D.SIFC_DX_DU_INT = 1 +00000000 NV50_2D.SIFC_DY_DV_FRACT = 0 +00000001 NV50_2D.SIFC_DY_DV_INT = 1 +00000000 NV50_2D.SIFC_DST_X_FRACT = 0 +00000000 NV50_2D.SIFC_DST_X_INT = 0 +00000000 NV50_2D.SIFC_DST_Y_FRACT = 0 +00000000 NV50_2D.SIFC_DST_Y_INT = 0 +40048860 size 1, subchannel 4 (0x5c0000d3), offset 0x0860, constant +00000003 NV50_2D.SIFC_DATA = 0x3 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000050 NVA3_COMPUTE.QUERY_SEQUENCE = 0x50 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000278 2010705c +# out of band: 0000027c 0000a200 +000441c0 size 1, subchannel 2 (0x5c0000d2), offset 0x01c0, increment +5c0000c5 NVA3_COMPUTE.DMA_CODE_CB = 0x5c0000c5 +00044210 size 1, subchannel 2 (0x5c0000d2), offset 0x0210, increment +000000fd NVA3_COMPUTE.CP_ADDRESS_HIGH = 0xfd +00044214 size 1, subchannel 2 (0x5c0000d2), offset 0x0214, increment +fffc0000 NVA3_COMPUTE.CP_ADDRESS_LOW = 0xfffc0000 +00044294 size 1, subchannel 2 (0x5c0000d2), offset 0x0294, increment +00000000 NVA3_COMPUTE.LOCAL_ADDRESS_HIGH = 0 +00044298 size 1, subchannel 2 (0x5c0000d2), offset 0x0298, increment +40000000 NVA3_COMPUTE.LOCAL_ADDRESS_LOW = 0x40000000 +0004429c size 1, subchannel 2 (0x5c0000d2), offset 0x029c, increment +00000006 NVA3_COMPUTE.LOCAL_SIZE_LOG = 6 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +000443b4 size 1, subchannel 2 (0x5c0000d2), offset 0x03b4, increment +00002c00 NVA3_COMPUTE.CP_START_ID = 0x2c00 +00044380 size 1, subchannel 2 (0x5c0000d2), offset 0x0380, increment +00000000 NVA3_COMPUTE.CODE_CB_FLUSH = 0 +000443ac size 1, subchannel 2 (0x5c0000d2), offset 0x03ac, increment +00010003 NVA3_COMPUTE.BLOCKDIM_XY = { X = 3 | Y = 1 } +000443b0 size 1, subchannel 2 (0x5c0000d2), offset 0x03b0, increment +00000001 NVA3_COMPUTE.BLOCKDIM_Z = 1 +000442b4 size 1, subchannel 2 (0x5c0000d2), offset 0x02b4, increment +00010003 NVA3_COMPUTE.BLOCK_ALLOC = { THREADS = 3 | BARRIERS = 1 } +000443a4 size 1, subchannel 2 (0x5c0000d2), offset 0x03a4, increment +00010003 NVA3_COMPUTE.GRIDDIM = { X = 3 | Y = 1 } +000442c0 size 1, subchannel 2 (0x5c0000d2), offset 0x02c0, increment +0000000a NVA3_COMPUTE.CP_REG_ALLOC_TEMP = 0xa +000443a8 size 1, subchannel 2 (0x5c0000d2), offset 0x03a8, increment +00000080 NVA3_COMPUTE.SHARED_SIZE = 0x80 +00044388 size 1, subchannel 2 (0x5c0000d2), offset 0x0388, increment +00000001 NVA3_COMPUTE.GRIDID = 0x1 +00044374 size 1, subchannel 2 (0x5c0000d2), offset 0x0374, increment +00000800 NVA3_COMPUTE.USER_PARAM_COUNT = { UNK0 = 0 | COUNT = 8 } +00204600 size 8, subchannel 2 (0x5c0000d2), offset 0x0600, increment +00220000 NVA3_COMPUTE.USER_PARAM[0] = 0x220000 +00000000 NVA3_COMPUTE.USER_PARAM[0x1] = 0 +00220100 NVA3_COMPUTE.USER_PARAM[0x2] = 0x220100 +00000000 NVA3_COMPUTE.USER_PARAM[0x3] = 0 +00220200 NVA3_COMPUTE.USER_PARAM[0x4] = 0x220200 +00000000 NVA3_COMPUTE.USER_PARAM[0x5] = 0 +00220300 NVA3_COMPUTE.USER_PARAM[0x6] = 0x220300 +00000000 NVA3_COMPUTE.USER_PARAM[0x7] = 0 +000442f8 size 1, subchannel 2 (0x5c0000d2), offset 0x02f8, increment +00000001 NVA3_COMPUTE.BLOCKDIM_LATCH = TRUE +00044368 size 1, subchannel 2 (0x5c0000d2), offset 0x0368, increment +00000000 NVA3_COMPUTE.LAUNCH = 0 +00044110 size 1, subchannel 2 (0x5c0000d2), offset 0x0110, increment +00000000 NVA3_COMPUTE.GRAPH.SERIALIZE = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000051 NVA3_COMPUTE.QUERY_SEQUENCE = 0x51 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000280 201070fc +# out of band: 00000284 0000da00 +00046200 size 1, subchannel 3 (0x5c0000d4), offset 0x0200, increment +00000001 NV50_M2MF.LINEAR_IN = TRUE +00046314 size 1, subchannel 3 (0x5c0000d4), offset 0x0314, increment +00040000 NV50_M2MF.PITCH_IN = 262144 +0004621c size 1, subchannel 3 (0x5c0000d4), offset 0x021c, increment +00000001 NV50_M2MF.LINEAR_OUT = TRUE +00046318 size 1, subchannel 3 (0x5c0000d4), offset 0x0318, increment +00040000 NV50_M2MF.PITCH_OUT = 262144 +00046324 size 1, subchannel 3 (0x5c0000d4), offset 0x0324, increment +00000101 NV50_M2MF.FORMAT = { INPUT_INC = 1 | OUTPUT_INC = 1 } +00046314 size 1, subchannel 3 (0x5c0000d4), offset 0x0314, increment +00000024 NV50_M2MF.PITCH_IN = 36 +00046318 size 1, subchannel 3 (0x5c0000d4), offset 0x0318, increment +00000024 NV50_M2MF.PITCH_OUT = 36 +00046238 size 1, subchannel 3 (0x5c0000d4), offset 0x0238, increment +000000ff NV50_M2MF.OFFSET_IN_HIGH = 0xff +0004630c size 1, subchannel 3 (0x5c0000d4), offset 0x030c, increment +00200000 NV50_M2MF.OFFSET_IN = 0x200000 +0004623c size 1, subchannel 3 (0x5c0000d4), offset 0x023c, increment +00000000 NV50_M2MF.OFFSET_OUT_HIGH = 0 +00046310 size 1, subchannel 3 (0x5c0000d4), offset 0x0310, increment +20b05000 NV50_M2MF.OFFSET_OUT = 0x20b05000 +0004631c size 1, subchannel 3 (0x5c0000d4), offset 0x031c, increment +00000024 NV50_M2MF.LINE_LENGTH_IN = 36 +00046320 size 1, subchannel 3 (0x5c0000d4), offset 0x0320, increment +00000001 NV50_M2MF.LINE_COUNT = 1 +00046328 size 1, subchannel 3 (0x5c0000d4), offset 0x0328, increment +00000000 NV50_M2MF.BUF_NOTIFY = 0 +00046100 size 1, subchannel 3 (0x5c0000d4), offset 0x0100, increment +00000000 NV50_M2MF.GRAPH.NOP = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000052 NVA3_COMPUTE.QUERY_SEQUENCE = 0x52 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000288 201071d4 +# out of band: 0000028c 00008e00 +00046200 size 1, subchannel 3 (0x5c0000d4), offset 0x0200, increment +00000001 NV50_M2MF.LINEAR_IN = TRUE +00046314 size 1, subchannel 3 (0x5c0000d4), offset 0x0314, increment +00040000 NV50_M2MF.PITCH_IN = 262144 +0004621c size 1, subchannel 3 (0x5c0000d4), offset 0x021c, increment +00000001 NV50_M2MF.LINEAR_OUT = TRUE +00046318 size 1, subchannel 3 (0x5c0000d4), offset 0x0318, increment +00040000 NV50_M2MF.PITCH_OUT = 262144 +00046324 size 1, subchannel 3 (0x5c0000d4), offset 0x0324, increment +00000101 NV50_M2MF.FORMAT = { INPUT_INC = 1 | OUTPUT_INC = 1 } +00046314 size 1, subchannel 3 (0x5c0000d4), offset 0x0314, increment +00000024 NV50_M2MF.PITCH_IN = 36 +00046318 size 1, subchannel 3 (0x5c0000d4), offset 0x0318, increment +00000024 NV50_M2MF.PITCH_OUT = 36 +00046238 size 1, subchannel 3 (0x5c0000d4), offset 0x0238, increment +000000ff NV50_M2MF.OFFSET_IN_HIGH = 0xff +0004630c size 1, subchannel 3 (0x5c0000d4), offset 0x030c, increment +00200100 NV50_M2MF.OFFSET_IN = 0x200100 +0004623c size 1, subchannel 3 (0x5c0000d4), offset 0x023c, increment +00000000 NV50_M2MF.OFFSET_OUT_HIGH = 0 +00046310 size 1, subchannel 3 (0x5c0000d4), offset 0x0310, increment +20905000 NV50_M2MF.OFFSET_OUT = 0x20905000 +0004631c size 1, subchannel 3 (0x5c0000d4), offset 0x031c, increment +00000024 NV50_M2MF.LINE_LENGTH_IN = 36 +00046320 size 1, subchannel 3 (0x5c0000d4), offset 0x0320, increment +00000001 NV50_M2MF.LINE_COUNT = 1 +00046328 size 1, subchannel 3 (0x5c0000d4), offset 0x0328, increment +00000000 NV50_M2MF.BUF_NOTIFY = 0 +00046100 size 1, subchannel 3 (0x5c0000d4), offset 0x0100, increment +00000000 NV50_M2MF.GRAPH.NOP = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000053 NVA3_COMPUTE.QUERY_SEQUENCE = 0x53 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# out of band: 00000290 20107260 +# out of band: 00000294 00008e00 +00046200 size 1, subchannel 3 (0x5c0000d4), offset 0x0200, increment +00000001 NV50_M2MF.LINEAR_IN = TRUE +00046314 size 1, subchannel 3 (0x5c0000d4), offset 0x0314, increment +00040000 NV50_M2MF.PITCH_IN = 262144 +0004621c size 1, subchannel 3 (0x5c0000d4), offset 0x021c, increment +00000001 NV50_M2MF.LINEAR_OUT = TRUE +00046318 size 1, subchannel 3 (0x5c0000d4), offset 0x0318, increment +00040000 NV50_M2MF.PITCH_OUT = 262144 +00046324 size 1, subchannel 3 (0x5c0000d4), offset 0x0324, increment +00000101 NV50_M2MF.FORMAT = { INPUT_INC = 1 | OUTPUT_INC = 1 } +00046314 size 1, subchannel 3 (0x5c0000d4), offset 0x0314, increment +00000024 NV50_M2MF.PITCH_IN = 36 +00046318 size 1, subchannel 3 (0x5c0000d4), offset 0x0318, increment +00000024 NV50_M2MF.PITCH_OUT = 36 +00046238 size 1, subchannel 3 (0x5c0000d4), offset 0x0238, increment +000000ff NV50_M2MF.OFFSET_IN_HIGH = 0xff +0004630c size 1, subchannel 3 (0x5c0000d4), offset 0x030c, increment +00200200 NV50_M2MF.OFFSET_IN = 0x200200 +0004623c size 1, subchannel 3 (0x5c0000d4), offset 0x023c, increment +00000000 NV50_M2MF.OFFSET_OUT_HIGH = 0 +00046310 size 1, subchannel 3 (0x5c0000d4), offset 0x0310, increment +20b05000 NV50_M2MF.OFFSET_OUT = 0x20b05000 +0004631c size 1, subchannel 3 (0x5c0000d4), offset 0x031c, increment +00000024 NV50_M2MF.LINE_LENGTH_IN = 36 +00046320 size 1, subchannel 3 (0x5c0000d4), offset 0x0320, increment +00000001 NV50_M2MF.LINE_COUNT = 1 +00046328 size 1, subchannel 3 (0x5c0000d4), offset 0x0328, increment +00000000 NV50_M2MF.BUF_NOTIFY = 0 +00046100 size 1, subchannel 3 (0x5c0000d4), offset 0x0100, increment +00000000 NV50_M2MF.GRAPH.NOP = 0 +00104310 size 4, subchannel 2 (0x5c0000d2), offset 0x0310, increment +00000000 NVA3_COMPUTE.QUERY_ADDRESS_HIGH = 0 +2000ffe0 NVA3_COMPUTE.QUERY_ADDRESS_LOW = 0x2000ffe0 +00000054 NVA3_COMPUTE.QUERY_SEQUENCE = 0x54 +00000000 NVA3_COMPUTE.QUERY_GET = { 0 } +# jump to 0x1072ec: 00000298 201072ec +00008e00 diff --git a/traces/matrix_mul_nvc4_dedmaed b/traces/matrix_mul_nvc4_dedmaed new file mode 100644 index 00000000..28303b62 --- /dev/null +++ b/traces/matrix_mul_nvc4_dedmaed @@ -0,0 +1,13080 @@ +20014000 size 1, subchannel 2 (0x0), offset 0x0000, increment +000090c0 NVC0_COMPUTE mapped to subchannel 2 +20014040 size 1, subchannel 2 (0x90c0), offset 0x0100, increment +00000000 NVC0_COMPUTE.GRAPH.NOP = 0 +200141d6 size 1, subchannel 2 (0x90c0), offset 0x0758, increment +00000007 NVC0_COMPUTE.MP_LIMIT = 0x7 +20014359 size 1, subchannel 2 (0x90c0), offset 0x0d64, increment +0000000f NVC0_COMPUTE.CALL_LIMIT_LOG = 0xf +200141e4 size 1, subchannel 2 (0x90c0), offset 0x0790, increment +00000000 NVC0_COMPUTE.TEMP_ADDRESS_HIGH = 0 +200141e5 size 1, subchannel 2 (0x90c0), offset 0x0794, increment +10000000 NVC0_COMPUTE.TEMP_ADDRESS_LOW = 0x10000000 +200141e6 size 1, subchannel 2 (0x90c0), offset 0x0798, increment +00000000 NVC0_COMPUTE.TEMP_SIZE_HIGH = 0 +200141e7 size 1, subchannel 2 (0x90c0), offset 0x079c, increment +01700000 NVC0_COMPUTE.TEMP_SIZE_LOW = 0x1700000 +200141e8 size 1, subchannel 2 (0x90c0), offset 0x07a0, increment +00011a00 NVC0_COMPUTE.WARP_TEMP_ALLOC = 0x11a00 +200141df size 1, subchannel 2 (0x90c0), offset 0x077c, increment +03000000 NVC0_COMPUTE.LOCAL_BASE = 0x3000000 +20014085 size 1, subchannel 2 (0x90c0), offset 0x0214, increment +01000000 NVC0_COMPUTE.SHARED_BASE = 0x1000000 +20014093 size 1, subchannel 2 (0x90c0), offset 0x024c, increment +00000000 NVC0_COMPUTE.SHARED_SIZE = 0 +200140a8 size 1, subchannel 2 (0x90c0), offset 0x02a0, increment +00008000 NVC0_COMPUTE.UNK02A0 = 0x8000 +2001408e size 1, subchannel 2 (0x90c0), offset 0x0238, increment +00010001 NVC0_COMPUTE.GRIDDIM_YX = { X = 1 | Y = 1 } +2001408f size 1, subchannel 2 (0x90c0), offset 0x023c, increment +00000001 NVC0_COMPUTE.GRIDDIM_Z = 1 +200140eb size 1, subchannel 2 (0x90c0), offset 0x03ac, increment +00010001 NVC0_COMPUTE.BLOCKDIM_YX = { X = 1 | Y = 1 } +200140ec size 1, subchannel 2 (0x90c0), offset 0x03b0, increment +00000001 NVC0_COMPUTE.BLOCKDIM_Z = 1 +200140b1 size 1, subchannel 2 (0x90c0), offset 0x02c4, increment +00000000 NVC0_COMPUTE.UNK02C4 = FALSE +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0000000 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0 | INDEX = 0 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0010001 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x1 | INDEX = 0x1 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0020002 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x2 | INDEX = 0x2 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0030003 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x3 | INDEX = 0x3 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0040004 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x4 | INDEX = 0x4 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0050005 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x5 | INDEX = 0x5 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0060006 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x6 | INDEX = 0x6 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0070007 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x7 | INDEX = 0x7 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0080008 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x8 | INDEX = 0x8 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0090009 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x9 | INDEX = 0x9 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c00a000a NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa | INDEX = 0xa | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c00b000b NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb | INDEX = 0xb | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c00c000c NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc | INDEX = 0xc | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c00d000d NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd | INDEX = 0xd | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c00e000e NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe | INDEX = 0xe | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c00f000f NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf | INDEX = 0xf | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0100010 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x10 | INDEX = 0x10 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0110011 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x11 | INDEX = 0x11 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0120012 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x12 | INDEX = 0x12 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0130013 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x13 | INDEX = 0x13 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0140014 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x14 | INDEX = 0x14 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0150015 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x15 | INDEX = 0x15 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0160016 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x16 | INDEX = 0x16 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0170017 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x17 | INDEX = 0x17 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0180018 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x18 | INDEX = 0x18 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0190019 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x19 | INDEX = 0x19 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c01a001a NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x1a | INDEX = 0x1a | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c01b001b NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x1b | INDEX = 0x1b | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c01c001c NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x1c | INDEX = 0x1c | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c01d001d NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x1d | INDEX = 0x1d | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c01e001e NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x1e | INDEX = 0x1e | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c01f001f NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x1f | INDEX = 0x1f | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0200020 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x20 | INDEX = 0x20 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0210021 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x21 | INDEX = 0x21 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0220022 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x22 | INDEX = 0x22 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0230023 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x23 | INDEX = 0x23 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0240024 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x24 | INDEX = 0x24 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0250025 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x25 | INDEX = 0x25 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0260026 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x26 | INDEX = 0x26 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0270027 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x27 | INDEX = 0x27 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0280028 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x28 | INDEX = 0x28 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0290029 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x29 | INDEX = 0x29 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c02a002a NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x2a | INDEX = 0x2a | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c02b002b NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x2b | INDEX = 0x2b | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c02c002c NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x2c | INDEX = 0x2c | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c02d002d NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x2d | INDEX = 0x2d | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c02e002e NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x2e | INDEX = 0x2e | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c02f002f NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x2f | INDEX = 0x2f | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0300030 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x30 | INDEX = 0x30 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0310031 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x31 | INDEX = 0x31 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0320032 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x32 | INDEX = 0x32 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0330033 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x33 | INDEX = 0x33 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0340034 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x34 | INDEX = 0x34 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0350035 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x35 | INDEX = 0x35 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0360036 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x36 | INDEX = 0x36 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0370037 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x37 | INDEX = 0x37 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0380038 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x38 | INDEX = 0x38 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0390039 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x39 | INDEX = 0x39 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c03a003a NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x3a | INDEX = 0x3a | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c03b003b NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x3b | INDEX = 0x3b | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c03c003c NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x3c | INDEX = 0x3c | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c03d003d NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x3d | INDEX = 0x3d | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c03e003e NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x3e | INDEX = 0x3e | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c03f003f NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x3f | INDEX = 0x3f | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0400040 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x40 | INDEX = 0x40 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0410041 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x41 | INDEX = 0x41 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0420042 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x42 | INDEX = 0x42 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0430043 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x43 | INDEX = 0x43 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0440044 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x44 | INDEX = 0x44 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0450045 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x45 | INDEX = 0x45 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0460046 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x46 | INDEX = 0x46 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0470047 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x47 | INDEX = 0x47 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0480048 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x48 | INDEX = 0x48 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0490049 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x49 | INDEX = 0x49 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c04a004a NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x4a | INDEX = 0x4a | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c04b004b NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x4b | INDEX = 0x4b | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c04c004c NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x4c | INDEX = 0x4c | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c04d004d NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x4d | INDEX = 0x4d | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c04e004e NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x4e | INDEX = 0x4e | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c04f004f NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x4f | INDEX = 0x4f | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0500050 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x50 | INDEX = 0x50 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0510051 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x51 | INDEX = 0x51 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0520052 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x52 | INDEX = 0x52 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0530053 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x53 | INDEX = 0x53 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0540054 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x54 | INDEX = 0x54 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0550055 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x55 | INDEX = 0x55 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0560056 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x56 | INDEX = 0x56 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0570057 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x57 | INDEX = 0x57 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0580058 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x58 | INDEX = 0x58 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0590059 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x59 | INDEX = 0x59 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c05a005a NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x5a | INDEX = 0x5a | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c05b005b NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x5b | INDEX = 0x5b | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c05c005c NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x5c | INDEX = 0x5c | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c05d005d NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x5d | INDEX = 0x5d | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c05e005e NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x5e | INDEX = 0x5e | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c05f005f NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x5f | INDEX = 0x5f | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0600060 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x60 | INDEX = 0x60 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0610061 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x61 | INDEX = 0x61 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0620062 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x62 | INDEX = 0x62 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0630063 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x63 | INDEX = 0x63 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0640064 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x64 | INDEX = 0x64 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0650065 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x65 | INDEX = 0x65 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0660066 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x66 | INDEX = 0x66 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0670067 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x67 | INDEX = 0x67 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0680068 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x68 | INDEX = 0x68 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0690069 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x69 | INDEX = 0x69 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c06a006a NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x6a | INDEX = 0x6a | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c06b006b NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x6b | INDEX = 0x6b | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c06c006c NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x6c | INDEX = 0x6c | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c06d006d NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x6d | INDEX = 0x6d | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c06e006e NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x6e | INDEX = 0x6e | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c06f006f NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x6f | INDEX = 0x6f | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0700070 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x70 | INDEX = 0x70 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0710071 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x71 | INDEX = 0x71 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0720072 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x72 | INDEX = 0x72 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0730073 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x73 | INDEX = 0x73 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0740074 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x74 | INDEX = 0x74 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0750075 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x75 | INDEX = 0x75 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0760076 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x76 | INDEX = 0x76 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0770077 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x77 | INDEX = 0x77 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0780078 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x78 | INDEX = 0x78 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0790079 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x79 | INDEX = 0x79 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c07a007a NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x7a | INDEX = 0x7a | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c07b007b NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x7b | INDEX = 0x7b | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c07c007c NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x7c | INDEX = 0x7c | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c07d007d NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x7d | INDEX = 0x7d | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c07e007e NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x7e | INDEX = 0x7e | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c07f007f NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x7f | INDEX = 0x7f | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0800080 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x80 | INDEX = 0x80 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0810081 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x81 | INDEX = 0x81 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0820082 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x82 | INDEX = 0x82 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0830083 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x83 | INDEX = 0x83 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0840084 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x84 | INDEX = 0x84 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0850085 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x85 | INDEX = 0x85 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0860086 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x86 | INDEX = 0x86 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0870087 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x87 | INDEX = 0x87 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0880088 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x88 | INDEX = 0x88 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0890089 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x89 | INDEX = 0x89 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c08a008a NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x8a | INDEX = 0x8a | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c08b008b NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x8b | INDEX = 0x8b | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c08c008c NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x8c | INDEX = 0x8c | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c08d008d NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x8d | INDEX = 0x8d | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c08e008e NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x8e | INDEX = 0x8e | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c08f008f NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x8f | INDEX = 0x8f | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0900090 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x90 | INDEX = 0x90 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0910091 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x91 | INDEX = 0x91 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0920092 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x92 | INDEX = 0x92 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0930093 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x93 | INDEX = 0x93 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0940094 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x94 | INDEX = 0x94 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0950095 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x95 | INDEX = 0x95 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0960096 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x96 | INDEX = 0x96 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0970097 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x97 | INDEX = 0x97 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0980098 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x98 | INDEX = 0x98 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0990099 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x99 | INDEX = 0x99 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c09a009a NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x9a | INDEX = 0x9a | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c09b009b NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x9b | INDEX = 0x9b | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c09c009c NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x9c | INDEX = 0x9c | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c09d009d NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x9d | INDEX = 0x9d | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c09e009e NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x9e | INDEX = 0x9e | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c09f009f NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0x9f | INDEX = 0x9f | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0a000a0 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa0 | INDEX = 0xa0 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0a100a1 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa1 | INDEX = 0xa1 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0a200a2 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa2 | INDEX = 0xa2 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0a300a3 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa3 | INDEX = 0xa3 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0a400a4 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa4 | INDEX = 0xa4 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0a500a5 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa5 | INDEX = 0xa5 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0a600a6 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa6 | INDEX = 0xa6 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0a700a7 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa7 | INDEX = 0xa7 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0a800a8 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa8 | INDEX = 0xa8 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0a900a9 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xa9 | INDEX = 0xa9 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0aa00aa NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xaa | INDEX = 0xaa | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ab00ab NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xab | INDEX = 0xab | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ac00ac NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xac | INDEX = 0xac | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ad00ad NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xad | INDEX = 0xad | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ae00ae NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xae | INDEX = 0xae | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0af00af NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xaf | INDEX = 0xaf | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0b000b0 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb0 | INDEX = 0xb0 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0b100b1 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb1 | INDEX = 0xb1 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0b200b2 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb2 | INDEX = 0xb2 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0b300b3 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb3 | INDEX = 0xb3 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0b400b4 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb4 | INDEX = 0xb4 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0b500b5 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb5 | INDEX = 0xb5 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0b600b6 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb6 | INDEX = 0xb6 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0b700b7 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb7 | INDEX = 0xb7 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0b800b8 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb8 | INDEX = 0xb8 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0b900b9 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xb9 | INDEX = 0xb9 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ba00ba NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xba | INDEX = 0xba | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0bb00bb NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xbb | INDEX = 0xbb | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0bc00bc NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xbc | INDEX = 0xbc | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0bd00bd NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xbd | INDEX = 0xbd | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0be00be NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xbe | INDEX = 0xbe | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0bf00bf NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xbf | INDEX = 0xbf | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0c000c0 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc0 | INDEX = 0xc0 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0c100c1 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc1 | INDEX = 0xc1 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0c200c2 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc2 | INDEX = 0xc2 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0c300c3 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc3 | INDEX = 0xc3 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0c400c4 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc4 | INDEX = 0xc4 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0c500c5 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc5 | INDEX = 0xc5 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0c600c6 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc6 | INDEX = 0xc6 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0c700c7 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc7 | INDEX = 0xc7 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0c800c8 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc8 | INDEX = 0xc8 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0c900c9 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xc9 | INDEX = 0xc9 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ca00ca NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xca | INDEX = 0xca | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0cb00cb NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xcb | INDEX = 0xcb | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0cc00cc NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xcc | INDEX = 0xcc | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0cd00cd NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xcd | INDEX = 0xcd | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ce00ce NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xce | INDEX = 0xce | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0cf00cf NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xcf | INDEX = 0xcf | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0d000d0 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd0 | INDEX = 0xd0 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0d100d1 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd1 | INDEX = 0xd1 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0d200d2 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd2 | INDEX = 0xd2 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0d300d3 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd3 | INDEX = 0xd3 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0d400d4 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd4 | INDEX = 0xd4 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0d500d5 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd5 | INDEX = 0xd5 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0d600d6 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd6 | INDEX = 0xd6 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0d700d7 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd7 | INDEX = 0xd7 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0d800d8 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd8 | INDEX = 0xd8 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0d900d9 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xd9 | INDEX = 0xd9 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0da00da NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xda | INDEX = 0xda | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0db00db NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xdb | INDEX = 0xdb | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0dc00dc NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xdc | INDEX = 0xdc | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0dd00dd NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xdd | INDEX = 0xdd | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0de00de NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xde | INDEX = 0xde | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0df00df NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xdf | INDEX = 0xdf | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0e000e0 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe0 | INDEX = 0xe0 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0e100e1 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe1 | INDEX = 0xe1 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0e200e2 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe2 | INDEX = 0xe2 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0e300e3 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe3 | INDEX = 0xe3 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0e400e4 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe4 | INDEX = 0xe4 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0e500e5 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe5 | INDEX = 0xe5 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0e600e6 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe6 | INDEX = 0xe6 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0e700e7 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe7 | INDEX = 0xe7 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0e800e8 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe8 | INDEX = 0xe8 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0e900e9 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xe9 | INDEX = 0xe9 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ea00ea NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xea | INDEX = 0xea | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0eb00eb NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xeb | INDEX = 0xeb | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ec00ec NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xec | INDEX = 0xec | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ed00ed NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xed | INDEX = 0xed | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ee00ee NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xee | INDEX = 0xee | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ef00ef NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xef | INDEX = 0xef | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0f000f0 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf0 | INDEX = 0xf0 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0f100f1 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf1 | INDEX = 0xf1 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0f200f2 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf2 | INDEX = 0xf2 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0f300f3 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf3 | INDEX = 0xf3 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0f400f4 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf4 | INDEX = 0xf4 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0f500f5 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf5 | INDEX = 0xf5 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0f600f6 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf6 | INDEX = 0xf6 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0f700f7 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf7 | INDEX = 0xf7 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0f800f8 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf8 | INDEX = 0xf8 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0f900f9 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xf9 | INDEX = 0xf9 | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0fa00fa NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xfa | INDEX = 0xfa | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0fb00fb NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xfb | INDEX = 0xfb | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0fc00fc NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xfc | INDEX = 0xfc | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0fd00fd NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xfd | INDEX = 0xfd | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0fe00fe NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xfe | INDEX = 0xfe | READ_OK | WRITE_OK } +200140b2 size 1, subchannel 2 (0x90c0), offset 0x02c8, increment +c0ff00ff NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0xff | INDEX = 0xff | READ_OK | WRITE_OK } +200140b1 size 1, subchannel 2 (0x90c0), offset 0x02c4, increment +00000001 NVC0_COMPUTE.UNK02C4 = TRUE +20016000 size 1, subchannel 3 (0x0), offset 0x0000, increment +00009039 NVC0_M2MF mapped to subchannel 3 +20018000 size 1, subchannel 4 (0x0), offset 0x0000, increment +0000902d NVC0_2D mapped to subchannel 4 +20014084 size 1, subchannel 2 (0x90c0), offset 0x0210, increment +00000033 NVC0_COMPUTE.TEX_LIMITS = { SAMPLERS_LOG2 = 3 | TEXTURES_LOG2 = 3 } +2001448d size 1, subchannel 2 (0x90c0), offset 0x1234, increment +00000001 NVC0_COMPUTE.LINKED_TSC = TRUE +2001455d size 1, subchannel 2 (0x90c0), offset 0x1574, increment +00000000 NVC0_COMPUTE.TIC_ADDRESS_HIGH = 0 +2001455e size 1, subchannel 2 (0x90c0), offset 0x1578, increment +11800000 NVC0_COMPUTE.TIC_ADDRESS_LOW = 0x11800000 +2001455f size 1, subchannel 2 (0x90c0), offset 0x157c, increment +000003ff NVC0_COMPUTE.TIC_LIMIT = 0x3ff +20014557 size 1, subchannel 2 (0x90c0), offset 0x155c, increment +00000000 NVC0_COMPUTE.TSC_ADDRESS_HIGH = 0 +20014558 size 1, subchannel 2 (0x90c0), offset 0x1560, increment +11808000 NVC0_COMPUTE.TSC_ADDRESS_LOW = 0x11808000 +20014559 size 1, subchannel 2 (0x90c0), offset 0x1564, increment +000003ff NVC0_COMPUTE.TSC_LIMIT = 0x3ff +200446c0 size 4, subchannel 2 (0x90c0), offset 0x1b00, increment +00000000 NVC0_COMPUTE.QUERY_ADDRESS_HIGH = 0 +0800ffd0 NVC0_COMPUTE.QUERY_ADDRESS_LOW = 0x800ffd0 +00000001 NVC0_COMPUTE.QUERY_SEQUENCE = 0x1 +00000000 NVC0_COMPUTE.QUERY_GET = { MODE = WRITE } +08102000 size 2064, subchannel 1 (0x0), offset 0x0000, increment +0008fe00 OBJFE00 mapped to subchannel 1 +081028fc OBJFE00.0x4 = 0x81028fc +000ac200 OBJFE00.0x8 = 0xac200 +081033bc OBJFE00.0xc = 0x81033bc +00002e00 OBJFE00.SUBCHAN.SEMAPHORE_ADDRESS_HIGH = 0x2e00 +081033e8 OBJFE00.SUBCHAN.SEMAPHORE_ADDRESS_LOW = 0x81033e8 +0003b200 OBJFE00.SUBCHAN.SEMAPHORE_SEQUENCE = 0x3b200 +08103798 OBJFE00.SUBCHAN.SEMAPHORE_TRIGGER = 0x8103798 +00001e00 OBJFE00.SUBCHAN.NOTIFY_INTR = 0x1e00 +081037b4 OBJFE00.SUBCHAN.WRCACHE_FLUSH = 0x81037b4 +0001ca00 OBJFE00.0x28 = 0x1ca00 +0810397c OBJFE00.0x2c = 0x810397c +00001e00 OBJFE00.0x30 = 0x1e00 +08103998 OBJFE00.0x34 = 0x8103998 +00029a00 OBJFE00.0x38 = 0x29a00 +08103c30 OBJFE00.0x3c = 0x8103c30 +00001e00 OBJFE00.0x40 = 0x1e00 +08103c4c OBJFE00.0x44 = 0x8103c4c +00022200 OBJFE00.0x48 = 0x22200 +08103e6c OBJFE00.0x4c = 0x8103e6c +00001e00 OBJFE00.SUBCHAN.REF_CNT = 0x1e00 +08103e88 OBJFE00.0x54 = 0x8103e88 +00010a00 OBJFE00.0x58 = 0x10a00 +08103f90 OBJFE00.0x5c = 0x8103f90 +00001e00 OBJFE00.SUBCHAN.DMA_SEMAPHORE = 0x1e00 +200348e0 OBJFE00.SUBCHAN.SEMAPHORE_OFFSET = 0x200348e0 +00010000 OBJFE00.SUBCHAN.SEMAPHORE_ACQUIRE = 0x10000 +00000001 OBJFE00.SUBCHAN.SEMAPHORE_RELEASE = 0x1 +00000000 OBJFE00.0x70 = 0 +200148e3 OBJFE00.0x74 = 0x200148e3 +00000000 OBJFE00.0x78 = 0 +62a448e4 OBJFE00.0x7c = 0x62a448e4 +e0000007 OBJFE00.SUBCHAN.YIELD = 0xe0000007 +7803ffff OBJFE00.0x84 = 0x7803ffff +00001de4 OBJFE00.0x88 = 0x1de4 +40000000 OBJFE00.0x8c = 0x40000000 +a0000007 OBJFE00.0x90 = 0xa0000007 +7803ffff OBJFE00.0x94 = 0x7803ffff +00001de4 OBJFE00.0x98 = 0x1de4 +40000000 OBJFE00.0x9c = 0x40000000 +60000007 OBJFE00.0xa0 = 0x60000007 +7803ffff OBJFE00.0xa4 = 0x7803ffff +00001de4 OBJFE00.0xa8 = 0x1de4 +40000000 OBJFE00.0xac = 0x40000000 +20000007 OBJFE00.0xb0 = 0x20000007 +7803ffff OBJFE00.0xb4 = 0x7803ffff +00001de4 OBJFE00.0xb8 = 0x1de4 +40000000 OBJFE00.0xbc = 0x40000000 +e0000007 OBJFE00.0xc0 = 0xe0000007 +7803fffe OBJFE00.0xc4 = 0x7803fffe +00001de4 OBJFE00.0xc8 = 0x1de4 +40000000 OBJFE00.0xcc = 0x40000000 +a0000007 OBJFE00.0xd0 = 0xa0000007 +7803fffe OBJFE00.0xd4 = 0x7803fffe +00001de4 OBJFE00.0xd8 = 0x1de4 +40000000 OBJFE00.0xdc = 0x40000000 +60000007 OBJFE00.0xe0 = 0x60000007 +7803fffe OBJFE00.0xe4 = 0x7803fffe +00001de4 OBJFE00.0xe8 = 0x1de4 +40000000 OBJFE00.0xec = 0x40000000 +20000007 OBJFE00.0xf0 = 0x20000007 +7803fffe OBJFE00.0xf4 = 0x7803fffe +00001de4 OBJFE00.0xf8 = 0x1de4 +40000000 OBJFE00.0xfc = 0x40000000 +e0000007 OBJFE00.0x100 = 0xe0000007 +7803fffd OBJFE00.0x104 = 0x7803fffd +00001de4 OBJFE00.0x108 = 0x1de4 +40000000 OBJFE00.0x10c = 0x40000000 +a0000007 OBJFE00.0x110 = 0xa0000007 +7803fffd OBJFE00.0x114 = 0x7803fffd +00001de4 OBJFE00.0x118 = 0x1de4 +40000000 OBJFE00.0x11c = 0x40000000 +60000007 OBJFE00.0x120 = 0x60000007 +7803fffd OBJFE00.0x124 = 0x7803fffd +00001de4 OBJFE00.0x128 = 0x1de4 +40000000 OBJFE00.0x12c = 0x40000000 +20000007 OBJFE00.0x130 = 0x20000007 +7803fffd OBJFE00.0x134 = 0x7803fffd +00001de4 OBJFE00.0x138 = 0x1de4 +40000000 OBJFE00.0x13c = 0x40000000 +e0000007 OBJFE00.0x140 = 0xe0000007 +7803fffc OBJFE00.0x144 = 0x7803fffc +00001de4 OBJFE00.0x148 = 0x1de4 +40000000 OBJFE00.0x14c = 0x40000000 +a0000007 OBJFE00.0x150 = 0xa0000007 +7803fffc OBJFE00.0x154 = 0x7803fffc +00001de4 OBJFE00.0x158 = 0x1de4 +40000000 OBJFE00.0x15c = 0x40000000 +60000007 OBJFE00.0x160 = 0x60000007 +7803fffc OBJFE00.0x164 = 0x7803fffc +00001de4 OBJFE00.0x168 = 0x1de4 +40000000 OBJFE00.0x16c = 0x40000000 +20000007 OBJFE00.0x170 = 0x20000007 +7803fffc OBJFE00.0x174 = 0x7803fffc +00001de4 OBJFE00.0x178 = 0x1de4 +40000000 OBJFE00.0x17c = 0x40000000 +e3ffdc85 OBJFE00.0x180 = 0xe3ffdc85 +c003ffff OBJFE00.0x184 = 0xc003ffff +03ffdcc5 OBJFE00.0x188 = 0x3ffdcc5 +d0000000 OBJFE00.0x18c = 0xd0000000 +03ffdcc5 OBJFE00.0x190 = 0x3ffdcc5 +98000000 OBJFE00.0x194 = 0x98000000 +00001c45 OBJFE00.0x198 = 0x1c45 +e0000000 OBJFE00.0x19c = 0xe0000000 +03f03de7 OBJFE00.0x1a0 = 0x3f03de7 +48000000 OBJFE00.0x1a4 = 0x48000000 +f3f01c85 OBJFE00.0x1a8 = 0xf3f01c85 +c803ffff OBJFE00.0x1ac = 0xc803ffff +00001de2 OBJFE00.0x1b0 = 0x1de2 +18040000 OBJFE00.0x1b4 = 0x18040000 +e0005c85 OBJFE00.0x1b8 = 0xe0005c85 +c803ffff OBJFE00.0x1bc = 0xc803ffff +d0009c85 OBJFE00.0x1c0 = 0xd0009c85 +c803ffff OBJFE00.0x1c4 = 0xc803ffff +c000dc85 OBJFE00.0x1c8 = 0xc000dc85 +c803ffff OBJFE00.0x1cc = 0xc803ffff +b0011c85 OBJFE00.0x1d0 = 0xb0011c85 +c803ffff OBJFE00.0x1d4 = 0xc803ffff +a0015c85 OBJFE00.0x1d8 = 0xa0015c85 +c803ffff OBJFE00.0x1dc = 0xc803ffff +90019c85 OBJFE00.0x1e0 = 0x90019c85 +c803ffff OBJFE00.0x1e4 = 0xc803ffff +8001dc85 OBJFE00.0x1e8 = 0x8001dc85 +c803ffff OBJFE00.0x1ec = 0xc803ffff +70021c85 OBJFE00.0x1f0 = 0x70021c85 +c803ffff OBJFE00.0x1f4 = 0xc803ffff +60025c85 OBJFE00.0x1f8 = 0x60025c85 +c803ffff OBJFE00.0x1fc = 0xc803ffff +50029c85 OBJFE00.0x200 = 0x50029c85 +c803ffff OBJFE00.0x204 = 0xc803ffff +4002dc85 OBJFE00.0x208 = 0x4002dc85 +c803ffff OBJFE00.0x20c = 0xc803ffff +30031c85 OBJFE00.0x210 = 0x30031c85 +c803ffff OBJFE00.0x214 = 0xc803ffff +20035c85 OBJFE00.0x218 = 0x20035c85 +c803ffff OBJFE00.0x21c = 0xc803ffff +10039c85 OBJFE00.0x220 = 0x10039c85 +c803ffff OBJFE00.0x224 = 0xc803ffff +0003dc85 OBJFE00.0x228 = 0x3dc85 +c803ffff OBJFE00.0x22c = 0xc803ffff +f0041c85 OBJFE00.0x230 = 0xf0041c85 +c803fffe OBJFE00.0x234 = 0xc803fffe +e0045c85 OBJFE00.0x238 = 0xe0045c85 +c803fffe OBJFE00.0x23c = 0xc803fffe +d0049c85 OBJFE00.0x240 = 0xd0049c85 +c803fffe OBJFE00.0x244 = 0xc803fffe +c004dc85 OBJFE00.0x248 = 0xc004dc85 +c803fffe OBJFE00.0x24c = 0xc803fffe +b0051c85 OBJFE00.0x250 = 0xb0051c85 +c803fffe OBJFE00.0x254 = 0xc803fffe +a0055c85 OBJFE00.0x258 = 0xa0055c85 +c803fffe OBJFE00.0x25c = 0xc803fffe +90059c85 OBJFE00.0x260 = 0x90059c85 +c803fffe OBJFE00.0x264 = 0xc803fffe +8005dc85 OBJFE00.0x268 = 0x8005dc85 +c803fffe OBJFE00.0x26c = 0xc803fffe +70061c85 OBJFE00.0x270 = 0x70061c85 +c803fffe OBJFE00.0x274 = 0xc803fffe +60065c85 OBJFE00.0x278 = 0x60065c85 +c803fffe OBJFE00.0x27c = 0xc803fffe +50069c85 OBJFE00.0x280 = 0x50069c85 +c803fffe OBJFE00.0x284 = 0xc803fffe +4006dc85 OBJFE00.0x288 = 0x4006dc85 +c803fffe OBJFE00.0x28c = 0xc803fffe +30071c85 OBJFE00.0x290 = 0x30071c85 +c803fffe OBJFE00.0x294 = 0xc803fffe +20075c85 OBJFE00.0x298 = 0x20075c85 +c803fffe OBJFE00.0x29c = 0xc803fffe +10079c85 OBJFE00.0x2a0 = 0x10079c85 +c803fffe OBJFE00.0x2a4 = 0xc803fffe +0007dc85 OBJFE00.0x2a8 = 0x7dc85 +c803fffe OBJFE00.0x2ac = 0xc803fffe +f0081c85 OBJFE00.0x2b0 = 0xf0081c85 +c803fffd OBJFE00.0x2b4 = 0xc803fffd +e0085c85 OBJFE00.0x2b8 = 0xe0085c85 +c803fffd OBJFE00.0x2bc = 0xc803fffd +d0089c85 OBJFE00.0x2c0 = 0xd0089c85 +c803fffd OBJFE00.0x2c4 = 0xc803fffd +c008dc85 OBJFE00.0x2c8 = 0xc008dc85 +c803fffd OBJFE00.0x2cc = 0xc803fffd +b0091c85 OBJFE00.0x2d0 = 0xb0091c85 +c803fffd OBJFE00.0x2d4 = 0xc803fffd +a0095c85 OBJFE00.0x2d8 = 0xa0095c85 +c803fffd OBJFE00.0x2dc = 0xc803fffd +90099c85 OBJFE00.0x2e0 = 0x90099c85 +c803fffd OBJFE00.0x2e4 = 0xc803fffd +8009dc85 OBJFE00.0x2e8 = 0x8009dc85 +c803fffd OBJFE00.0x2ec = 0xc803fffd +700a1c85 OBJFE00.0x2f0 = 0x700a1c85 +c803fffd OBJFE00.0x2f4 = 0xc803fffd +600a5c85 OBJFE00.0x2f8 = 0x600a5c85 +c803fffd OBJFE00.0x2fc = 0xc803fffd +500a9c85 OBJFE00.0x300 = 0x500a9c85 +c803fffd OBJFE00.0x304 = 0xc803fffd +400adc85 OBJFE00.0x308 = 0x400adc85 +c803fffd OBJFE00.0x30c = 0xc803fffd +300b1c85 OBJFE00.0x310 = 0x300b1c85 +c803fffd OBJFE00.0x314 = 0xc803fffd +200b5c85 OBJFE00.0x318 = 0x200b5c85 +c803fffd OBJFE00.0x31c = 0xc803fffd +100b9c85 OBJFE00.0x320 = 0x100b9c85 +c803fffd OBJFE00.0x324 = 0xc803fffd +000bdc85 OBJFE00.0x328 = 0xbdc85 +c803fffd OBJFE00.0x32c = 0xc803fffd +f00c1c85 OBJFE00.0x330 = 0xf00c1c85 +c803fffc OBJFE00.0x334 = 0xc803fffc +e00c5c85 OBJFE00.0x338 = 0xe00c5c85 +c803fffc OBJFE00.0x33c = 0xc803fffc +d00c9c85 OBJFE00.0x340 = 0xd00c9c85 +c803fffc OBJFE00.0x344 = 0xc803fffc +c00cdc85 OBJFE00.0x348 = 0xc00cdc85 +c803fffc OBJFE00.0x34c = 0xc803fffc +b00d1c85 OBJFE00.0x350 = 0xb00d1c85 +c803fffc OBJFE00.0x354 = 0xc803fffc +a00d5c85 OBJFE00.0x358 = 0xa00d5c85 +c803fffc OBJFE00.0x35c = 0xc803fffc +900d9c85 OBJFE00.0x360 = 0x900d9c85 +c803fffc OBJFE00.0x364 = 0xc803fffc +800ddc85 OBJFE00.0x368 = 0x800ddc85 +c803fffc OBJFE00.0x36c = 0xc803fffc +700e1c85 OBJFE00.0x370 = 0x700e1c85 +c803fffc OBJFE00.0x374 = 0xc803fffc +600e5c85 OBJFE00.0x378 = 0x600e5c85 +c803fffc OBJFE00.0x37c = 0xc803fffc +500e9c85 OBJFE00.0x380 = 0x500e9c85 +c803fffc OBJFE00.0x384 = 0xc803fffc +400edc85 OBJFE00.0x388 = 0x400edc85 +c803fffc OBJFE00.0x38c = 0xc803fffc +300f1c85 OBJFE00.0x390 = 0x300f1c85 +c803fffc OBJFE00.0x394 = 0xc803fffc +200f5c85 OBJFE00.0x398 = 0x200f5c85 +c803fffc OBJFE00.0x39c = 0xc803fffc +100f9c85 OBJFE00.0x3a0 = 0x100f9c85 +c803fffc OBJFE00.0x3a4 = 0xc803fffc +000fdc85 OBJFE00.0x3a8 = 0xfdc85 +c803fffc OBJFE00.0x3ac = 0xc803fffc +fff05c04 OBJFE00.0x3b0 = 0xfff05c04 +3000c3ff OBJFE00.0x3b4 = 0x3000c3ff +10005c85 OBJFE00.0x3b8 = 0x10005c85 +c803fffb OBJFE00.0x3bc = 0xc803fffb +00005de2 OBJFE00.0x3c0 = 0x5de2 +18800000 OBJFE00.0x3c4 = 0x18800000 +f0005c85 OBJFE00.0x3c8 = 0xf0005c85 +c803fffb OBJFE00.0x3cc = 0xc803fffb +04009de2 OBJFE00.0x3d0 = 0x4009de2 +18000000 OBJFE00.0x3d4 = 0x18000000 +00109c85 OBJFE00.0x3d8 = 0x109c85 +90000000 OBJFE00.0x3dc = 0x90000000 +40001de2 OBJFE00.0x3e0 = 0x40001de2 +18000000 OBJFE00.0x3e4 = 0x18000000 +04001c03 OBJFE00.0x3e8 = 0x4001c03 +48000000 OBJFE00.0x3ec = 0x48000000 +0c009c04 OBJFE00.0x3f0 = 0xc009c04 +2c000000 OBJFE00.0x3f4 = 0x2c000000 +50209c23 OBJFE00.0x3f8 = 0x50209c23 +5800c000 OBJFE00.0x3fc = 0x5800c000 +fc209c03 OBJFE00.0x400 = 0xfc209c03 +6800c007 OBJFE00.0x404 = 0x6800c007 +0800dc04 OBJFE00.0x408 = 0x800dc04 +2c000000 OBJFE00.0x40c = 0x2c000000 +2030dc23 OBJFE00.0x410 = 0x2030dc23 +5800c000 OBJFE00.0x414 = 0x5800c000 +fc30dc03 OBJFE00.0x418 = 0xfc30dc03 +6800c001 OBJFE00.0x41c = 0x6800c001 +0c209ca3 OBJFE00.0x420 = 0xc209ca3 +50000000 OBJFE00.0x424 = 0x50000000 +2000dde2 OBJFE00.0x428 = 0x2000dde2 +18000005 OBJFE00.0x42c = 0x18000005 +0c209ca3 OBJFE00.0x430 = 0xc209ca3 +50000000 OBJFE00.0x434 = 0x50000000 +08001c03 OBJFE00.0x438 = 0x8001c03 +48000000 OBJFE00.0x43c = 0x48000000 +0c009c04 OBJFE00.0x440 = 0xc009c04 +2c000000 OBJFE00.0x444 = 0x2c000000 +20209c23 OBJFE00.0x448 = 0x20209c23 +5800c000 OBJFE00.0x44c = 0x5800c000 +fc209c03 OBJFE00.0x450 = 0xfc209c03 +6800c000 OBJFE00.0x454 = 0x6800c000 +0c209ca3 OBJFE00.0x458 = 0xc209ca3 +50000000 OBJFE00.0x45c = 0x50000000 +08001c03 OBJFE00.0x460 = 0x8001c03 +48000000 OBJFE00.0x464 = 0x48000000 +00009c04 OBJFE00.0x468 = 0x9c04 +2c000000 OBJFE00.0x46c = 0x2c000000 +fc23dc23 OBJFE00.0x470 = 0xfc23dc23 +190e0000 OBJFE00.0x474 = 0x190e0000 +0c00c404 OBJFE00.0x478 = 0xc00c404 +2c000000 OBJFE00.0x47c = 0x2c000000 +0000c485 OBJFE00.0x480 = 0xc485 +90000000 OBJFE00.0x484 = 0x90000000 +9000c404 OBJFE00.0x488 = 0x9000c404 +2c000000 OBJFE00.0x48c = 0x2c000000 +1000c485 OBJFE00.0x490 = 0x1000c485 +90000000 OBJFE00.0x494 = 0x90000000 +9400c404 OBJFE00.0x498 = 0x9400c404 +2c000000 OBJFE00.0x49c = 0x2c000000 +2000c485 OBJFE00.0x4a0 = 0x2000c485 +90000000 OBJFE00.0x4a4 = 0x90000000 +9800c404 OBJFE00.0x4a8 = 0x9800c404 +2c000000 OBJFE00.0x4ac = 0x2c000000 +3000c485 OBJFE00.0x4b0 = 0x3000c485 +90000000 OBJFE00.0x4b4 = 0x90000000 +9c00c404 OBJFE00.0x4b8 = 0x9c00c404 +2c000000 OBJFE00.0x4bc = 0x2c000000 +4000c485 OBJFE00.0x4c0 = 0x4000c485 +90000000 OBJFE00.0x4c4 = 0x90000000 +a400c404 OBJFE00.0x4c8 = 0xa400c404 +2c000000 OBJFE00.0x4cc = 0x2c000000 +5000c485 OBJFE00.0x4d0 = 0x5000c485 +90000000 OBJFE00.0x4d4 = 0x90000000 +a800c404 OBJFE00.0x4d8 = 0xa800c404 +2c000000 OBJFE00.0x4dc = 0x2c000000 +6000c485 OBJFE00.0x4e0 = 0x6000c485 +90000000 OBJFE00.0x4e4 = 0x90000000 +ac00c404 OBJFE00.0x4e8 = 0xac00c404 +2c000000 OBJFE00.0x4ec = 0x2c000000 +7000c485 OBJFE00.0x4f0 = 0x7000c485 +90000000 OBJFE00.0x4f4 = 0x90000000 +b000c404 OBJFE00.0x4f8 = 0xb000c404 +2c000000 OBJFE00.0x4fc = 0x2c000000 +8000c485 OBJFE00.0x500 = 0x8000c485 +90000000 OBJFE00.0x504 = 0x90000000 +b400c404 OBJFE00.0x508 = 0xb400c404 +2c000000 OBJFE00.0x50c = 0x2c000000 +9000c485 OBJFE00.0x510 = 0x9000c485 +90000000 OBJFE00.0x514 = 0x90000000 +b800c404 OBJFE00.0x518 = 0xb800c404 +2c000000 OBJFE00.0x51c = 0x2c000000 +a000c485 OBJFE00.0x520 = 0xa000c485 +90000000 OBJFE00.0x524 = 0x90000000 +bc00c404 OBJFE00.0x528 = 0xbc00c404 +2c000000 OBJFE00.0x52c = 0x2c000000 +b000c485 OBJFE00.0x530 = 0xb000c485 +90000000 OBJFE00.0x534 = 0x90000000 +c800c404 OBJFE00.0x538 = 0xc800c404 +2c000000 OBJFE00.0x53c = 0x2c000000 +c000c485 OBJFE00.0x540 = 0xc000c485 +90000000 OBJFE00.0x544 = 0x90000000 +d400c404 OBJFE00.0x548 = 0xd400c404 +2c000000 OBJFE00.0x54c = 0x2c000000 +d000c485 OBJFE00.0x550 = 0xd000c485 +90000000 OBJFE00.0x554 = 0x90000000 +d800c404 OBJFE00.0x558 = 0xd800c404 +2c000000 OBJFE00.0x55c = 0x2c000000 +e000c485 OBJFE00.0x560 = 0xe000c485 +90000000 OBJFE00.0x564 = 0x90000000 +dc00c404 OBJFE00.0x568 = 0xdc00c404 +2c000000 OBJFE00.0x56c = 0x2c000000 +f000c485 OBJFE00.0x570 = 0xf000c485 +90000000 OBJFE00.0x574 = 0x90000000 +0000c404 OBJFE00.0x578 = 0xc404 +2c000001 OBJFE00.0x57c = 0x2c000001 +0000c485 OBJFE00.0x580 = 0xc485 +90000001 OBJFE00.0x584 = 0x90000001 +0800c404 OBJFE00.0x588 = 0x800c404 +2c000001 OBJFE00.0x58c = 0x2c000001 +1000c485 OBJFE00.0x590 = 0x1000c485 +90000001 OBJFE00.0x594 = 0x90000001 +20001c03 OBJFE00.0x598 = 0x20001c03 +4800c001 OBJFE00.0x59c = 0x4800c001 +20209ca2 OBJFE00.0x5a0 = 0x20209ca2 +10000000 OBJFE00.0x5a4 = 0x10000000 +08001c03 OBJFE00.0x5a8 = 0x8001c03 +48000000 OBJFE00.0x5ac = 0x48000000 +80009c04 OBJFE00.0x5b0 = 0x80009c04 +2c000000 OBJFE00.0x5b4 = 0x2c000000 +00009c85 OBJFE00.0x5b8 = 0x9c85 +90000000 OBJFE00.0x5bc = 0x90000000 +e3f09c85 OBJFE00.0x5c0 = 0xe3f09c85 +c003ffff OBJFE00.0x5c4 = 0xc003ffff +10009c85 OBJFE00.0x5c8 = 0x10009c85 +90000000 OBJFE00.0x5cc = 0x90000000 +03ffdcc5 OBJFE00.0x5d0 = 0x3ffdcc5 +d0000000 OBJFE00.0x5d4 = 0xd0000000 +03ffdcc5 OBJFE00.0x5d8 = 0x3ffdcc5 +98000000 OBJFE00.0x5dc = 0x98000000 +00001c45 OBJFE00.0x5e0 = 0x1c45 +e0000000 OBJFE00.0x5e4 = 0xe0000000 +00009c04 OBJFE00.0x5e8 = 0x9c04 +2c000001 OBJFE00.0x5ec = 0x2c000001 +c4209c02 OBJFE00.0x5f0 = 0xc4209c02 +3800000f OBJFE00.0x5f4 = 0x3800000f +0021dc23 OBJFE00.0x5f8 = 0x21dc23 +190ec000 OBJFE00.0x5fc = 0x190ec000 +08009c04 OBJFE00.0x600 = 0x8009c04 +2c000001 OBJFE00.0x604 = 0x2c000001 +fc209c02 OBJFE00.0x608 = 0xfc209c02 +3a000003 OBJFE00.0x60c = 0x3a000003 +0021c023 OBJFE00.0x610 = 0x21c023 +190ec000 OBJFE00.0x614 = 0x190ec000 +400001e7 OBJFE00.0x618 = 0x400001e7 +4000000b OBJFE00.0x61c = 0x4000000b +00001de2 OBJFE00.0x620 = 0x1de2 +18040000 OBJFE00.0x624 = 0x18040000 +e00fdc85 OBJFE00.0x628 = 0xe00fdc85 +c803fffa OBJFE00.0x62c = 0xc803fffa +03ffdcc5 OBJFE00.0x630 = 0x3ffdcc5 +d0000000 OBJFE00.0x634 = 0xd0000000 +03ffdcc5 OBJFE00.0x638 = 0x3ffdcc5 +98000000 OBJFE00.0x63c = 0x98000000 +00001c45 OBJFE00.0x640 = 0x1c45 +e0000000 OBJFE00.0x644 = 0xe0000000 +00008007 OBJFE00.0x648 = 0x8007 +d0000000 OBJFE00.0x64c = 0xd0000000 +03ffdcc5 OBJFE00.0x650 = 0x3ffdcc5 +d0000000 OBJFE00.0x654 = 0xd0000000 +03ffdcc5 OBJFE00.0x658 = 0x3ffdcc5 +98000000 OBJFE00.0x65c = 0x98000000 +00001c45 OBJFE00.0x660 = 0x1c45 +e0000000 OBJFE00.0x664 = 0xe0000000 +e0009c85 OBJFE00.0x668 = 0xe0009c85 +c003fffa OBJFE00.0x66c = 0xc003fffa +fc21dc23 OBJFE00.0x670 = 0xfc21dc23 +190e0000 OBJFE00.0x674 = 0x190e0000 +c00001e7 OBJFE00.0x678 = 0xc00001e7 +40000009 OBJFE00.0x67c = 0x40000009 +0400dde2 OBJFE00.0x680 = 0x400dde2 +18000000 OBJFE00.0x684 = 0x18000000 +0831dc23 OBJFE00.0x688 = 0x831dc23 +190e0000 OBJFE00.0x68c = 0x190e0000 +e00001e7 OBJFE00.0x690 = 0xe00001e7 +40000000 OBJFE00.0x694 = 0x40000000 +0800dde2 OBJFE00.0x698 = 0x800dde2 +18000000 OBJFE00.0x69c = 0x18000000 +0831dc23 OBJFE00.0x6a0 = 0x831dc23 +190e0000 OBJFE00.0x6a4 = 0x190e0000 +800001e7 OBJFE00.0x6a8 = 0x800001e7 +40000000 OBJFE00.0x6ac = 0x40000000 +1400dde2 OBJFE00.0x6b0 = 0x1400dde2 +18000000 OBJFE00.0x6b4 = 0x18000000 +0831dc23 OBJFE00.0x6b8 = 0x831dc23 +190e0000 OBJFE00.0x6bc = 0x190e0000 +400001e7 OBJFE00.0x6c0 = 0x400001e7 +40000007 OBJFE00.0x6c4 = 0x40000007 +80001de7 OBJFE00.0x6c8 = 0x80001de7 +40000008 OBJFE00.0x6cc = 0x40000008 +00001de2 OBJFE00.0x6d0 = 0x1de2 +18040000 OBJFE00.0x6d4 = 0x18040000 +00009c04 OBJFE00.0x6d8 = 0x9c04 +2c000000 OBJFE00.0x6dc = 0x2c000000 +fc23dc23 OBJFE00.0x6e0 = 0xfc23dc23 +190e0000 OBJFE00.0x6e4 = 0x190e0000 +f0005c85 OBJFE00.0x6e8 = 0xf0005c85 +c003fffb OBJFE00.0x6ec = 0xc003fffb +40105c02 OBJFE00.0x6f0 = 0x40105c02 +08000f60 OBJFE00.0x6f4 = 0x8000f60 +0c009c04 OBJFE00.0x6f8 = 0xc009c04 +2c000000 OBJFE00.0x6fc = 0x2c000000 +40209c23 OBJFE00.0x700 = 0x40209c23 +5800c000 OBJFE00.0x704 = 0x5800c000 +3c209c03 OBJFE00.0x708 = 0x3c209c03 +6800c000 OBJFE00.0x70c = 0x6800c000 +c800dc04 OBJFE00.0x710 = 0xc800dc04 +2c000000 OBJFE00.0x714 = 0x2c000000 +fc30dc03 OBJFE00.0x718 = 0xfc30dc03 +6800c3ff OBJFE00.0x71c = 0x6800c3ff +0c209ca3 OBJFE00.0x720 = 0xc209ca3 +50000000 OBJFE00.0x724 = 0x50000000 +08105c03 OBJFE00.0x728 = 0x8105c03 +48000000 OBJFE00.0x72c = 0x48000000 +0c009c04 OBJFE00.0x730 = 0xc009c04 +2c000000 OBJFE00.0x734 = 0x2c000000 +50209c23 OBJFE00.0x738 = 0x50209c23 +5800c000 OBJFE00.0x73c = 0x5800c000 +fc209c03 OBJFE00.0x740 = 0xfc209c03 +6800c007 OBJFE00.0x744 = 0x6800c007 +00209ca2 OBJFE00.0x748 = 0x209ca2 +10000300 OBJFE00.0x74c = 0x10000300 +08105c03 OBJFE00.0x750 = 0x8105c03 +48000000 OBJFE00.0x754 = 0x48000000 +e0009c85 OBJFE00.0x758 = 0xe0009c85 +c003fffa OBJFE00.0x75c = 0xc003fffa +0400dde2 OBJFE00.0x760 = 0x400dde2 +18000000 OBJFE00.0x764 = 0x18000000 +0831dc23 OBJFE00.0x768 = 0x831dc23 +190e0000 OBJFE00.0x76c = 0x190e0000 +fc009de4 OBJFE00.0x770 = 0xfc009de4 +28000000 OBJFE00.0x774 = 0x28000000 +c800dc04 OBJFE00.0x778 = 0xc800dc04 +2c000000 OBJFE00.0x77c = 0x2c000000 +fc30dc03 OBJFE00.0x780 = 0xfc30dc03 +6800c3ff OBJFE00.0x784 = 0x6800c3ff +200001e7 OBJFE00.0x788 = 0x200001e7 +40000002 OBJFE00.0x78c = 0x40000002 +e0009c85 OBJFE00.0x790 = 0xe0009c85 +c003fffa OBJFE00.0x794 = 0xc003fffa +0800dde2 OBJFE00.0x798 = 0x800dde2 +18000000 OBJFE00.0x79c = 0x18000000 +0831dc23 OBJFE00.0x7a0 = 0x831dc23 +190e0000 OBJFE00.0x7a4 = 0x190e0000 +fc009de4 OBJFE00.0x7a8 = 0xfc009de4 +28000000 OBJFE00.0x7ac = 0x28000000 +c800dc04 OBJFE00.0x7b0 = 0xc800dc04 +2c000000 OBJFE00.0x7b4 = 0x2c000000 +fc30dc03 OBJFE00.0x7b8 = 0xfc30dc03 +6800c3ff OBJFE00.0x7bc = 0x6800c3ff +e00001e7 OBJFE00.0x7c0 = 0xe00001e7 +40000002 OBJFE00.0x7c4 = 0x40000002 +00200485 OBJFE00.0x7c8 = 0x200485 +c1000000 OBJFE00.0x7cc = 0xc1000000 +00100485 OBJFE00.0x7d0 = 0x100485 +90000000 OBJFE00.0x7d4 = 0x90000000 +10200485 OBJFE00.0x7d8 = 0x10200485 +c1000000 OBJFE00.0x7dc = 0xc1000000 +10100485 OBJFE00.0x7e0 = 0x10100485 +90000000 OBJFE00.0x7e4 = 0x90000000 +20200485 OBJFE00.0x7e8 = 0x20200485 +c1000000 OBJFE00.0x7ec = 0xc1000000 +20100485 OBJFE00.0x7f0 = 0x20100485 +90000000 OBJFE00.0x7f4 = 0x90000000 +30200485 OBJFE00.0x7f8 = 0x30200485 +c1000000 OBJFE00.0x7fc = 0xc1000000 +30100485 OBJFE00.0x800 = 0x30100485 +90000000 OBJFE00.0x804 = 0x90000000 +40105c02 OBJFE00.0x808 = 0x40105c02 +08000000 OBJFE00.0x80c = 0x8000000 +40209c02 OBJFE00.0x810 = 0x40209c02 +08000000 OBJFE00.0x814 = 0x8000000 +0c21dc23 OBJFE00.0x818 = 0xc21dc23 +188e0000 OBJFE00.0x81c = 0x188e0000 +800001e7 OBJFE00.0x820 = 0x800001e7 +4003fffe OBJFE00.0x824 = 0x4003fffe +c0001de7 OBJFE00.0x828 = 0xc0001de7 +4003fff7 OBJFE00.0x82c = 0x4003fff7 +00100485 OBJFE00.0x830 = 0x100485 +80000000 OBJFE00.0x834 = 0x80000000 +00200485 OBJFE00.0x838 = 0x200485 +c9000000 OBJFE00.0x83c = 0xc9000000 +10100485 OBJFE00.0x840 = 0x10100485 +80000000 OBJFE00.0x844 = 0x80000000 +10200485 OBJFE00.0x848 = 0x10200485 +c9000000 OBJFE00.0x84c = 0xc9000000 +20100485 OBJFE00.0x850 = 0x20100485 +80000000 OBJFE00.0x854 = 0x80000000 +20200485 OBJFE00.0x858 = 0x20200485 +c9000000 OBJFE00.0x85c = 0xc9000000 +30100485 OBJFE00.0x860 = 0x30100485 +80000000 OBJFE00.0x864 = 0x80000000 +30200485 OBJFE00.0x868 = 0x30200485 +c9000000 OBJFE00.0x86c = 0xc9000000 +40105c02 OBJFE00.0x870 = 0x40105c02 +08000000 OBJFE00.0x874 = 0x8000000 +40209c02 OBJFE00.0x878 = 0x40209c02 +08000000 OBJFE00.0x87c = 0x8000000 +0c21dc23 OBJFE00.0x880 = 0xc21dc23 +188e0000 OBJFE00.0x884 = 0x188e0000 +800001e7 OBJFE00.0x888 = 0x800001e7 +4003fffe OBJFE00.0x88c = 0x4003fffe +20001de7 OBJFE00.0x890 = 0x20001de7 +4003fff6 OBJFE00.0x894 = 0x4003fff6 +00001c04 OBJFE00.0x898 = 0x1c04 +2c000000 OBJFE00.0x89c = 0x2c000000 +fc01dc23 OBJFE00.0x8a0 = 0xfc01dc23 +190e0000 OBJFE00.0x8a4 = 0x190e0000 +000101e2 OBJFE00.0x8a8 = 0x101e2 +18040000 OBJFE00.0x8ac = 0x18040000 +b0400085 OBJFE00.0x8b0 = 0xb0400085 +c003fffb OBJFE00.0x8b4 = 0xc003fffb +c0404085 OBJFE00.0x8b8 = 0xc0404085 +c003fffb OBJFE00.0x8bc = 0xc003fffb +d0408085 OBJFE00.0x8c0 = 0xd0408085 +c003fffb OBJFE00.0x8c4 = 0xc003fffb +e040c085 OBJFE00.0x8c8 = 0xe040c085 +c003fffb OBJFE00.0x8cc = 0xc003fffb +fc010086 OBJFE00.0x8d0 = 0xfc010086 +9003c001 OBJFE00.0x8d4 = 0x9003c001 +000001e2 OBJFE00.0x8d8 = 0x1e2 +18040000 OBJFE00.0x8dc = 0x18040000 +b0010085 OBJFE00.0x8e0 = 0xb0010085 +c803fffb OBJFE00.0x8e4 = 0xc803fffb +c0001de7 OBJFE00.0x8e8 = 0xc0001de7 +4003fff4 OBJFE00.0x8ec = 0x4003fff4 +00001de2 OBJFE00.0x8f0 = 0x1de2 +18040000 OBJFE00.0x8f4 = 0x18040000 +10005c85 OBJFE00.0x8f8 = 0x10005c85 +c003fffb OBJFE00.0x8fc = 0xc003fffb +fc101c04 OBJFE00.0x900 = 0xfc101c04 +3400c3ff OBJFE00.0x904 = 0x3400c3ff +000fdc85 OBJFE00.0x908 = 0xfdc85 +c003fffc OBJFE00.0x90c = 0xc003fffc +100f9c85 OBJFE00.0x910 = 0x100f9c85 +c003fffc OBJFE00.0x914 = 0xc003fffc +200f5c85 OBJFE00.0x918 = 0x200f5c85 +c003fffc OBJFE00.0x91c = 0xc003fffc +300f1c85 OBJFE00.0x920 = 0x300f1c85 +c003fffc OBJFE00.0x924 = 0xc003fffc +400edc85 OBJFE00.0x928 = 0x400edc85 +c003fffc OBJFE00.0x92c = 0xc003fffc +500e9c85 OBJFE00.0x930 = 0x500e9c85 +c003fffc OBJFE00.0x934 = 0xc003fffc +600e5c85 OBJFE00.0x938 = 0x600e5c85 +c003fffc OBJFE00.0x93c = 0xc003fffc +700e1c85 OBJFE00.0x940 = 0x700e1c85 +c003fffc OBJFE00.0x944 = 0xc003fffc +800ddc85 OBJFE00.0x948 = 0x800ddc85 +c003fffc OBJFE00.0x94c = 0xc003fffc +900d9c85 OBJFE00.0x950 = 0x900d9c85 +c003fffc OBJFE00.0x954 = 0xc003fffc +a00d5c85 OBJFE00.0x958 = 0xa00d5c85 +c003fffc OBJFE00.0x95c = 0xc003fffc +b00d1c85 OBJFE00.0x960 = 0xb00d1c85 +c003fffc OBJFE00.0x964 = 0xc003fffc +c00cdc85 OBJFE00.0x968 = 0xc00cdc85 +c003fffc OBJFE00.0x96c = 0xc003fffc +d00c9c85 OBJFE00.0x970 = 0xd00c9c85 +c003fffc OBJFE00.0x974 = 0xc003fffc +e00c5c85 OBJFE00.0x978 = 0xe00c5c85 +c003fffc OBJFE00.0x97c = 0xc003fffc +f00c1c85 OBJFE00.0x980 = 0xf00c1c85 +c003fffc OBJFE00.0x984 = 0xc003fffc +000bdc85 OBJFE00.0x988 = 0xbdc85 +c003fffd OBJFE00.0x98c = 0xc003fffd +100b9c85 OBJFE00.0x990 = 0x100b9c85 +c003fffd OBJFE00.0x994 = 0xc003fffd +200b5c85 OBJFE00.0x998 = 0x200b5c85 +c003fffd OBJFE00.0x99c = 0xc003fffd +300b1c85 OBJFE00.0x9a0 = 0x300b1c85 +c003fffd OBJFE00.0x9a4 = 0xc003fffd +400adc85 OBJFE00.0x9a8 = 0x400adc85 +c003fffd OBJFE00.0x9ac = 0xc003fffd +500a9c85 OBJFE00.0x9b0 = 0x500a9c85 +c003fffd OBJFE00.0x9b4 = 0xc003fffd +600a5c85 OBJFE00.0x9b8 = 0x600a5c85 +c003fffd OBJFE00.0x9bc = 0xc003fffd +700a1c85 OBJFE00.0x9c0 = 0x700a1c85 +c003fffd OBJFE00.0x9c4 = 0xc003fffd +8009dc85 OBJFE00.0x9c8 = 0x8009dc85 +c003fffd OBJFE00.0x9cc = 0xc003fffd +90099c85 OBJFE00.0x9d0 = 0x90099c85 +c003fffd OBJFE00.0x9d4 = 0xc003fffd +a0095c85 OBJFE00.0x9d8 = 0xa0095c85 +c003fffd OBJFE00.0x9dc = 0xc003fffd +b0091c85 OBJFE00.0x9e0 = 0xb0091c85 +c003fffd OBJFE00.0x9e4 = 0xc003fffd +c008dc85 OBJFE00.0x9e8 = 0xc008dc85 +c003fffd OBJFE00.0x9ec = 0xc003fffd +d0089c85 OBJFE00.0x9f0 = 0xd0089c85 +c003fffd OBJFE00.0x9f4 = 0xc003fffd +e0085c85 OBJFE00.0x9f8 = 0xe0085c85 +c003fffd OBJFE00.0x9fc = 0xc003fffd +f0081c85 OBJFE00.0xa00 = 0xf0081c85 +c003fffd OBJFE00.0xa04 = 0xc003fffd +0007dc85 OBJFE00.0xa08 = 0x7dc85 +c003fffe OBJFE00.0xa0c = 0xc003fffe +10079c85 OBJFE00.0xa10 = 0x10079c85 +c003fffe OBJFE00.0xa14 = 0xc003fffe +20075c85 OBJFE00.0xa18 = 0x20075c85 +c003fffe OBJFE00.0xa1c = 0xc003fffe +30071c85 OBJFE00.0xa20 = 0x30071c85 +c003fffe OBJFE00.0xa24 = 0xc003fffe +4006dc85 OBJFE00.0xa28 = 0x4006dc85 +c003fffe OBJFE00.0xa2c = 0xc003fffe +50069c85 OBJFE00.0xa30 = 0x50069c85 +c003fffe OBJFE00.0xa34 = 0xc003fffe +60065c85 OBJFE00.0xa38 = 0x60065c85 +c003fffe OBJFE00.0xa3c = 0xc003fffe +70061c85 OBJFE00.0xa40 = 0x70061c85 +c003fffe OBJFE00.0xa44 = 0xc003fffe +8005dc85 OBJFE00.0xa48 = 0x8005dc85 +c003fffe OBJFE00.0xa4c = 0xc003fffe +90059c85 OBJFE00.0xa50 = 0x90059c85 +c003fffe OBJFE00.0xa54 = 0xc003fffe +a0055c85 OBJFE00.0xa58 = 0xa0055c85 +c003fffe OBJFE00.0xa5c = 0xc003fffe +b0051c85 OBJFE00.0xa60 = 0xb0051c85 +c003fffe OBJFE00.0xa64 = 0xc003fffe +c004dc85 OBJFE00.0xa68 = 0xc004dc85 +c003fffe OBJFE00.0xa6c = 0xc003fffe +d0049c85 OBJFE00.0xa70 = 0xd0049c85 +c003fffe OBJFE00.0xa74 = 0xc003fffe +e0045c85 OBJFE00.0xa78 = 0xe0045c85 +c003fffe OBJFE00.0xa7c = 0xc003fffe +f0041c85 OBJFE00.0xa80 = 0xf0041c85 +c003fffe OBJFE00.0xa84 = 0xc003fffe +0003dc85 OBJFE00.0xa88 = 0x3dc85 +c003ffff OBJFE00.0xa8c = 0xc003ffff +10039c85 OBJFE00.0xa90 = 0x10039c85 +c003ffff OBJFE00.0xa94 = 0xc003ffff +20035c85 OBJFE00.0xa98 = 0x20035c85 +c003ffff OBJFE00.0xa9c = 0xc003ffff +30031c85 OBJFE00.0xaa0 = 0x30031c85 +c003ffff OBJFE00.0xaa4 = 0xc003ffff +4002dc85 OBJFE00.0xaa8 = 0x4002dc85 +c003ffff OBJFE00.0xaac = 0xc003ffff +50029c85 OBJFE00.0xab0 = 0x50029c85 +c003ffff OBJFE00.0xab4 = 0xc003ffff +60025c85 OBJFE00.0xab8 = 0x60025c85 +c003ffff OBJFE00.0xabc = 0xc003ffff +70021c85 OBJFE00.0xac0 = 0x70021c85 +c003ffff OBJFE00.0xac4 = 0xc003ffff +8001dc85 OBJFE00.0xac8 = 0x8001dc85 +c003ffff OBJFE00.0xacc = 0xc003ffff +90019c85 OBJFE00.0xad0 = 0x90019c85 +c003ffff OBJFE00.0xad4 = 0xc003ffff +a0015c85 OBJFE00.0xad8 = 0xa0015c85 +c003ffff OBJFE00.0xadc = 0xc003ffff +b0011c85 OBJFE00.0xae0 = 0xb0011c85 +c003ffff OBJFE00.0xae4 = 0xc003ffff +c000dc85 OBJFE00.0xae8 = 0xc000dc85 +c003ffff OBJFE00.0xaec = 0xc003ffff +d0009c85 OBJFE00.0xaf0 = 0xd0009c85 +c003ffff OBJFE00.0xaf4 = 0xc003ffff +e0005c85 OBJFE00.0xaf8 = 0xe0005c85 +c003ffff OBJFE00.0xafc = 0xc003ffff +f3f01c85 OBJFE00.0xb00 = 0xf3f01c85 +c003ffff OBJFE00.0xb04 = 0xc003ffff +00000007 OBJFE00.0xb08 = 0x7 +a0000000 OBJFE00.0xb0c = 0xa0000000 +200446c0 OBJFE00.0xb10 = 0x200446c0 +00000000 OBJFE00.0xb14 = 0 +0800ffd0 OBJFE00.0xb18 = 0x800ffd0 +00000002 OBJFE00.0xb1c = 0x2 +00000000 OBJFE00.0xb20 = 0 +20034d00 OBJFE00.0xb24 = 0x20034d00 +00000000 OBJFE00.0xb28 = 0 +00000000 OBJFE00.0xb2c = 0 +ffffffff OBJFE00.0xb30 = 0xffffffff +20014144 OBJFE00.0xb34 = 0x20014144 +00419e58 OBJFE00.0xb38 = 0x419e58 +200446c0 OBJFE00.0xb3c = 0x200446c0 +00000000 OBJFE00.0xb40 = 0 +0800ffd0 OBJFE00.0xb44 = 0x800ffd0 +00000003 OBJFE00.0xb48 = 0x3 +00000000 OBJFE00.0xb4c = 0 +200348e0 OBJFE00.0xb50 = 0x200348e0 +00010000 OBJFE00.0xb54 = 0x10000 +00000001 OBJFE00.0xb58 = 0x1 +00002700 OBJFE00.0xb5c = 0x2700 +200148e3 OBJFE00.0xb60 = 0x200148e3 +00000000 OBJFE00.0xb64 = 0 +60e048e4 OBJFE00.0xb68 = 0x60e048e4 +00005de4 OBJFE00.0xb6c = 0x5de4 +28004404 OBJFE00.0xb70 = 0x28004404 +9800dc04 OBJFE00.0xb74 = 0x9800dc04 +2c000000 OBJFE00.0xb78 = 0x2c000000 +94021c04 OBJFE00.0xb7c = 0x94021c04 +2c000000 OBJFE00.0xb80 = 0x2c000000 +84019c04 OBJFE00.0xb84 = 0x84019c04 +2c000000 OBJFE00.0xb88 = 0x2c000000 +20301c03 OBJFE00.0xb8c = 0x20301c03 +50014001 OBJFE00.0xb90 = 0x50014001 +20309c43 OBJFE00.0xb94 = 0x20309c43 +20ff4001 OBJFE00.0xb98 = 0x20ff4001 +30331c03 OBJFE00.0xb9c = 0x30331c03 +20844001 OBJFE00.0xba0 = 0x20844001 +40311c03 OBJFE00.0xba4 = 0x40311c03 +50014001 OBJFE00.0xba8 = 0x50014001 +20809c03 OBJFE00.0xbac = 0x20809c03 +200c4000 OBJFE00.0xbb0 = 0x200c4000 +40315c43 OBJFE00.0xbb4 = 0x40315c43 +20ff4001 OBJFE00.0xbb8 = 0x20ff4001 +50315c03 OBJFE00.0xbbc = 0x50315c03 +208a4001 OBJFE00.0xbc0 = 0x208a4001 +a0229d03 OBJFE00.0xbc4 = 0xa0229d03 +48014001 OBJFE00.0xbc8 = 0x48014001 +80009c03 OBJFE00.0xbcc = 0x80009c03 +48004000 OBJFE00.0xbd0 = 0x48004000 +b3f25d43 OBJFE00.0xbd4 = 0xb3f25d43 +48004001 OBJFE00.0xbd8 = 0x48004001 +0c20dc03 OBJFE00.0xbdc = 0xc20dc03 +6800c000 OBJFE00.0xbe0 = 0x6800c000 +1030de03 OBJFE00.0xbe4 = 0x1030de03 +4800c000 OBJFE00.0xbe8 = 0x4800c000 +0c31dc03 OBJFE00.0xbec = 0xc31dc03 +6800c000 OBJFE00.0xbf0 = 0x6800c000 +c070de03 OBJFE00.0xbf4 = 0xc070de03 +48014000 OBJFE00.0xbf8 = 0x48014000 +d3f2de43 OBJFE00.0xbfc = 0xd3f2de43 +48004000 OBJFE00.0xc00 = 0x48004000 +0830dc03 OBJFE00.0xc04 = 0x830dc03 +5800c000 OBJFE00.0xc08 = 0x5800c000 +800fdc03 OBJFE00.0xc0c = 0x800fdc03 +48014000 OBJFE00.0xc10 = 0x48014000 +d0001de4 OBJFE00.0xc14 = 0xd0001de4 +28004000 OBJFE00.0xc18 = 0x28004000 +0cb2dfc3 OBJFE00.0xc1c = 0xcb2dfc3 +40000000 OBJFE00.0xc20 = 0x40000000 +90c0dc43 OBJFE00.0xc24 = 0x90c0dc43 +48004000 OBJFE00.0xc28 = 0x48004000 +2cafdd03 OBJFE00.0xc2c = 0x2cafdd03 +48010000 OBJFE00.0xc30 = 0x48010000 +c002dde4 OBJFE00.0xc34 = 0xc002dde4 +28004000 OBJFE00.0xc38 = 0x28004000 +fc91dc63 OBJFE00.0xc3c = 0xfc91dc63 +188e0000 OBJFE00.0xc40 = 0x188e0000 +fcafdd03 OBJFE00.0xc44 = 0xfcafdd03 +48010000 OBJFE00.0xc48 = 0x48010000 +fc91dc63 OBJFE00.0xc4c = 0xfc91dc63 +1b000000 OBJFE00.0xc50 = 0x1b000000 +0cbfdd03 OBJFE00.0xc54 = 0xcbfdd03 +4801c000 OBJFE00.0xc58 = 0x4801c000 +fc01dc43 OBJFE00.0xc5c = 0xfc01dc43 +1a000000 OBJFE00.0xc60 = 0x1a000000 +a0411c03 OBJFE00.0xc64 = 0xa0411c03 +48014000 OBJFE00.0xc68 = 0x48014000 +08001de4 OBJFE00.0xc6c = 0x8001de4 +28000000 OBJFE00.0xc70 = 0x28000000 +b0515c43 OBJFE00.0xc74 = 0xb0515c43 +48004000 OBJFE00.0xc78 = 0x48004000 +e00021e7 OBJFE00.0xc7c = 0xe00021e7 +40000003 OBJFE00.0xc80 = 0x40000003 +03ffde03 OBJFE00.0xc84 = 0x3ffde03 +48014001 OBJFE00.0xc88 = 0x48014001 +10019de4 OBJFE00.0xc8c = 0x10019de4 +28004001 OBJFE00.0xc90 = 0x28004001 +fc61dc43 OBJFE00.0xc94 = 0xfc61dc43 +190e0000 OBJFE00.0xc98 = 0x190e0000 +000001e7 OBJFE00.0xc9c = 0x1e7 +80000000 OBJFE00.0xca0 = 0x80000000 +78a19c03 OBJFE00.0xca4 = 0x78a19c03 +5800c000 OBJFE00.0xca8 = 0x5800c000 +08a31c03 OBJFE00.0xcac = 0x8a31c03 +6000c000 OBJFE00.0xcb0 = 0x6000c000 +fc02dde4 OBJFE00.0xcb4 = 0xfc02dde4 +28000000 OBJFE00.0xcb8 = 0x28000000 +fc029de4 OBJFE00.0xcbc = 0xfc029de4 +28000000 OBJFE00.0xcc0 = 0x28000000 +18935c43 OBJFE00.0xcc4 = 0x18935c43 +40000000 OBJFE00.0xcc8 = 0x40000000 +30721c03 OBJFE00.0xccc = 0x30721c03 +48010000 OBJFE00.0xcd0 = 0x48010000 +37f25c43 OBJFE00.0xcd4 = 0x37f25c43 +48000000 OBJFE00.0xcd8 = 0x48000000 +10819c03 OBJFE00.0xcdc = 0x10819c03 +48010000 OBJFE00.0xce0 = 0x48010000 +1491dc43 OBJFE00.0xce4 = 0x1491dc43 +48000000 OBJFE00.0xce8 = 0x48000000 +04b2dc03 OBJFE00.0xcec = 0x4b2dc03 +4801c000 OBJFE00.0xcf0 = 0x4801c000 +00619c85 OBJFE00.0xcf4 = 0x619c85 +84000000 OBJFE00.0xcf8 = 0x84000000 +fca29c43 OBJFE00.0xcfc = 0xfca29c43 +48000000 OBJFE00.0xd00 = 0x48000000 +08821c03 OBJFE00.0xd04 = 0x8821c03 +48010000 OBJFE00.0xd08 = 0x48010000 +0c01dc03 OBJFE00.0xd0c = 0xc01dc03 +6800c000 OBJFE00.0xd10 = 0x6800c000 +0c925c43 OBJFE00.0xd14 = 0xc925c43 +48000000 OBJFE00.0xd18 = 0x48000000 +00bfdd03 OBJFE00.0xd1c = 0xbfdd03 +48014001 OBJFE00.0xd20 = 0x48014001 +1071de03 OBJFE00.0xd24 = 0x1071de03 +4800c000 OBJFE00.0xd28 = 0x4800c000 +60001c03 OBJFE00.0xd2c = 0x60001c03 +48004001 OBJFE00.0xd30 = 0x48004001 +10a1dc43 OBJFE00.0xd34 = 0x10a1dc43 +188e4001 OBJFE00.0xd38 = 0x188e4001 +60209c03 OBJFE00.0xd3c = 0x60209c03 +48014001 OBJFE00.0xd40 = 0x48014001 +0c71dc03 OBJFE00.0xd44 = 0xc71dc03 +6800c000 OBJFE00.0xd48 = 0x6800c000 +7030dc43 OBJFE00.0xd4c = 0x7030dc43 +48004001 OBJFE00.0xd50 = 0x48004001 +80411c03 OBJFE00.0xd54 = 0x80411c03 +48014001 OBJFE00.0xd58 = 0x48014001 +90515c43 OBJFE00.0xd5c = 0x90515c43 +48004001 OBJFE00.0xd60 = 0x48004001 +00819c85 OBJFE00.0xd64 = 0x819c85 +94000000 OBJFE00.0xd68 = 0x94000000 +600001e7 OBJFE00.0xd6c = 0x600001e7 +4003fffd OBJFE00.0xd70 = 0x4003fffd +a0001de7 OBJFE00.0xd74 = 0xa0001de7 +40000005 OBJFE00.0xd78 = 0x40000005 +c06fdd03 OBJFE00.0xd7c = 0xc06fdd03 +48014000 OBJFE00.0xd80 = 0x48014000 +50025de4 OBJFE00.0xd84 = 0x50025de4 +28004000 OBJFE00.0xd88 = 0x28004000 +d3f1dc43 OBJFE00.0xd8c = 0xd3f1dc43 +188e4000 OBJFE00.0xd90 = 0x188e4000 +fc925c03 OBJFE00.0xd94 = 0xfc925c03 +4800ffff OBJFE00.0xd98 = 0x4800ffff +2481dc03 OBJFE00.0xd9c = 0x2481dc03 +19000000 OBJFE00.0xda0 = 0x19000000 +000021e7 OBJFE00.0xda4 = 0x21e7 +80000000 OBJFE00.0xda8 = 0x80000000 +03ffde03 OBJFE00.0xdac = 0x3ffde03 +48014001 OBJFE00.0xdb0 = 0x48014001 +10021de4 OBJFE00.0xdb4 = 0x10021de4 +28004001 OBJFE00.0xdb8 = 0x28004001 +fc81dc43 OBJFE00.0xdbc = 0xfc81dc43 +190e0000 OBJFE00.0xdc0 = 0x190e0000 +000001e7 OBJFE00.0xdc4 = 0x1e7 +80000000 OBJFE00.0xdc8 = 0x80000000 +fc029de4 OBJFE00.0xdcc = 0xfc029de4 +28000000 OBJFE00.0xdd0 = 0x28000000 +fc02dde4 OBJFE00.0xdd4 = 0xfc02dde4 +28000000 OBJFE00.0xdd8 = 0x28000000 +1871dc03 OBJFE00.0xddc = 0x1871dc03 +198e0000 OBJFE00.0xde0 = 0x198e0000 +c00081e7 OBJFE00.0xde4 = 0xc00081e7 +40000000 OBJFE00.0xde8 = 0x40000000 +10632003 OBJFE00.0xdec = 0x10632003 +48010000 OBJFE00.0xdf0 = 0x48010000 +17f36043 OBJFE00.0xdf4 = 0x17f36043 +48000000 OBJFE00.0xdf8 = 0x48000000 +08622003 OBJFE00.0xdfc = 0x8622003 +48010000 OBJFE00.0xe00 = 0x48010000 +00c1e005 OBJFE00.0xe04 = 0xc1e005 +84000000 OBJFE00.0xe08 = 0x84000000 +0ff26043 OBJFE00.0xe0c = 0xff26043 +48000000 OBJFE00.0xe10 = 0x48000000 +0081e005 OBJFE00.0xe14 = 0x81e005 +94000000 OBJFE00.0xe18 = 0x94000000 +c021dc03 OBJFE00.0xe1c = 0xc021dc03 +48004000 OBJFE00.0xe20 = 0x48004000 +0c71dc03 OBJFE00.0xe24 = 0xc71dc03 +6800c000 OBJFE00.0xe28 = 0x6800c000 +1c61dc03 OBJFE00.0xe2c = 0x1c61dc03 +1b0e0000 OBJFE00.0xe30 = 0x1b0e0000 +000081e7 OBJFE00.0xe34 = 0x81e7 +40000001 OBJFE00.0xe38 = 0x40000001 +c0622203 OBJFE00.0xe3c = 0xc0622203 +48014000 OBJFE00.0xe40 = 0x48014000 +d3f26243 OBJFE00.0xe44 = 0xd3f26243 +48004000 OBJFE00.0xe48 = 0x48004000 +10832003 OBJFE00.0xe4c = 0x10832003 +48010000 OBJFE00.0xe50 = 0x48010000 +14936043 OBJFE00.0xe54 = 0x14936043 +48000000 OBJFE00.0xe58 = 0x48000000 +08822003 OBJFE00.0xe5c = 0x8822003 +48010000 OBJFE00.0xe60 = 0x48010000 +fcc1e005 OBJFE00.0xe64 = 0xfcc1e005 +87ffffff OBJFE00.0xe68 = 0x87ffffff +0c926043 OBJFE00.0xe6c = 0xc926043 +48000000 OBJFE00.0xe70 = 0x48000000 +fc81e005 OBJFE00.0xe74 = 0xfc81e005 +97ffffff OBJFE00.0xe78 = 0x97ffffff +60209c03 OBJFE00.0xe7c = 0x60209c03 +48014001 OBJFE00.0xe80 = 0x48014001 +0c01dc03 OBJFE00.0xe84 = 0xc01dc03 +6800c000 OBJFE00.0xe88 = 0x6800c000 +60001c03 OBJFE00.0xe8c = 0x60001c03 +48004001 OBJFE00.0xe90 = 0x48004001 +7030dc43 OBJFE00.0xe94 = 0x7030dc43 +48004001 OBJFE00.0xe98 = 0x48004001 +80411c03 OBJFE00.0xe9c = 0x80411c03 +48014001 OBJFE00.0xea0 = 0x48014001 +1071de03 OBJFE00.0xea4 = 0x1071de03 +4800c000 OBJFE00.0xea8 = 0x4800c000 +90515c43 OBJFE00.0xeac = 0x90515c43 +48004001 OBJFE00.0xeb0 = 0x48004001 +04a29c03 OBJFE00.0xeb4 = 0x4a29c03 +4801c000 OBJFE00.0xeb8 = 0x4801c000 +0c71dc03 OBJFE00.0xebc = 0xc71dc03 +6800c000 OBJFE00.0xec0 = 0x6800c000 +fcb2dc43 OBJFE00.0xec4 = 0xfcb2dc43 +48000000 OBJFE00.0xec8 = 0x48000000 +00afdd03 OBJFE00.0xecc = 0xafdd03 +48014001 OBJFE00.0xed0 = 0x48014001 +10b1dc43 OBJFE00.0xed4 = 0x10b1dc43 +188e4001 OBJFE00.0xed8 = 0x188e4001 +e00001e7 OBJFE00.0xedc = 0xe00001e7 +4003fffb OBJFE00.0xee0 = 0x4003fffb +00001de7 OBJFE00.0xee4 = 0x1de7 +80000000 OBJFE00.0xee8 = 0x80000000 +200446c0 OBJFE00.0xeec = 0x200446c0 +00000000 OBJFE00.0xef0 = 0 +0800ffd0 OBJFE00.0xef4 = 0x800ffd0 +00000004 OBJFE00.0xef8 = 0x4 +00000000 OBJFE00.0xefc = 0 +200145a6 OBJFE00.0xf00 = 0x200145a6 +00000001 OBJFE00.0xf04 = 0x1 +200446c0 OBJFE00.0xf08 = 0x200446c0 +00000000 OBJFE00.0xf0c = 0 +0800ffd0 OBJFE00.0xf10 = 0x800ffd0 +00000005 OBJFE00.0xf14 = 0x5 +00000000 OBJFE00.0xf18 = 0 +200348e0 OBJFE00.0xf1c = 0x200348e0 +00010000 OBJFE00.0xf20 = 0x10000 +00000001 OBJFE00.0xf24 = 0x1 +00002500 OBJFE00.0xf28 = 0x2500 +200148e3 OBJFE00.0xf2c = 0x200148e3 +00000000 OBJFE00.0xf30 = 0 +606648e4 OBJFE00.0xf34 = 0x606648e4 +00005de4 OBJFE00.0xf38 = 0x5de4 +28004404 OBJFE00.0xf3c = 0x28004404 +03ffde03 OBJFE00.0xf40 = 0x3ffde03 +48014001 OBJFE00.0xf44 = 0x48014001 +10009de4 OBJFE00.0xf48 = 0x10009de4 +28004001 OBJFE00.0xf4c = 0x28004001 +98001c04 OBJFE00.0xf50 = 0x98001c04 +2c000000 OBJFE00.0xf54 = 0x2c000000 +fc21dc43 OBJFE00.0xf58 = 0xfc21dc43 +190e0000 OBJFE00.0xf5c = 0x190e0000 +2000dc03 OBJFE00.0xf60 = 0x2000dc03 +50014001 OBJFE00.0xf64 = 0x50014001 +20009c43 OBJFE00.0xf68 = 0x20009c43 +20ff4001 OBJFE00.0xf6c = 0x20ff4001 +30009c03 OBJFE00.0xf70 = 0x30009c03 +20844001 OBJFE00.0xf74 = 0x20844001 +40015c03 OBJFE00.0xf78 = 0x40015c03 +50014001 OBJFE00.0xf7c = 0x50014001 +40011c43 OBJFE00.0xf80 = 0x40011c43 +20ff4001 OBJFE00.0xf84 = 0x20ff4001 +50019c03 OBJFE00.0xf88 = 0x50019c03 +20884001 OBJFE00.0xf8c = 0x20884001 +80301c03 OBJFE00.0xf90 = 0x80301c03 +48014000 OBJFE00.0xf94 = 0x48014000 +90211c43 OBJFE00.0xf98 = 0x90211c43 +48004000 OBJFE00.0xf9c = 0x48004000 +a0515c03 OBJFE00.0xfa0 = 0xa0515c03 +48014000 OBJFE00.0xfa4 = 0x48014000 +b0619c43 OBJFE00.0xfa8 = 0xb0619c43 +48004000 OBJFE00.0xfac = 0x48004000 +000001e7 OBJFE00.0xfb0 = 0x1e7 +80000000 OBJFE00.0xfb4 = 0x80000000 +94009c04 OBJFE00.0xfb8 = 0x94009c04 +2c000000 OBJFE00.0xfbc = 0x2c000000 +8400dc04 OBJFE00.0xfc0 = 0x8400dc04 +2c000000 OBJFE00.0xfc4 = 0x2c000000 +d0025de4 OBJFE00.0xfc8 = 0xd0025de4 +28004000 OBJFE00.0xfcc = 0x28004000 +fc02dde4 OBJFE00.0xfd0 = 0xfc02dde4 +28000000 OBJFE00.0xfd4 = 0x28000000 +20209c03 OBJFE00.0xfd8 = 0x20209c03 +20064000 OBJFE00.0xfdc = 0x20064000 +fc031de4 OBJFE00.0xfe0 = 0xfc031de4 +28000000 OBJFE00.0xfe4 = 0x28000000 +a0209d03 OBJFE00.0xfe8 = 0xa0209d03 +48014001 OBJFE00.0xfec = 0x48014001 +b3f0dd43 OBJFE00.0xff0 = 0xb3f0dd43 +48004001 OBJFE00.0xff4 = 0x48004001 +78221c03 OBJFE00.0xff8 = 0x78221c03 +5800c000 OBJFE00.0xffc = 0x5800c000 +0821dc03 OBJFE00.0x1000 = 0x821dc03 +6000c000 OBJFE00.0x1004 = 0x6000c000 +20335c43 OBJFE00.0x1008 = 0x20335c43 +40000000 OBJFE00.0x100c = 0x40000000 +c07fde03 OBJFE00.0x1010 = 0xc07fde03 +48014000 OBJFE00.0x1014 = 0x48014000 +1d209e84 OBJFE00.0x1018 = 0x1d209e84 +1c000000 OBJFE00.0x101c = 0x1c000000 +3491dc63 OBJFE00.0x1020 = 0x3491dc63 +1a0e0000 OBJFE00.0x1024 = 0x1a0e0000 +07f0dc23 OBJFE00.0x1028 = 0x7f0dc23 +3084c000 OBJFE00.0x102c = 0x3084c000 +07f09c04 OBJFE00.0x1030 = 0x7f09c04 +2010c000 OBJFE00.0x1034 = 0x2010c000 +0c229c03 OBJFE00.0x1038 = 0xc229c03 +68000000 OBJFE00.0x103c = 0x68000000 +fca1dc23 OBJFE00.0x1040 = 0xfca1dc23 +190e0000 OBJFE00.0x1044 = 0x190e0000 +c00081e7 OBJFE00.0x1048 = 0xc00081e7 +40000000 OBJFE00.0x104c = 0x40000000 +1c522003 OBJFE00.0x1050 = 0x1c522003 +48010000 OBJFE00.0x1054 = 0x48010000 +34626043 OBJFE00.0x1058 = 0x34626043 +48000000 OBJFE00.0x105c = 0x48000000 +1c00a003 OBJFE00.0x1060 = 0x1c00a003 +48010000 OBJFE00.0x1064 = 0x48010000 +00822085 OBJFE00.0x1068 = 0x822085 +84000000 OBJFE00.0x106c = 0x84000000 +3440e043 OBJFE00.0x1070 = 0x3440e043 +48000000 OBJFE00.0x1074 = 0x48000000 +00222085 OBJFE00.0x1078 = 0x222085 +94000000 OBJFE00.0x107c = 0x94000000 +60001c03 OBJFE00.0x1080 = 0x60001c03 +48014001 OBJFE00.0x1084 = 0x48014001 +70411c43 OBJFE00.0x1088 = 0x70411c43 +48004001 OBJFE00.0x108c = 0x48004001 +04b2dc03 OBJFE00.0x1090 = 0x4b2dc03 +4801c000 OBJFE00.0x1094 = 0x4801c000 +fcc31c43 OBJFE00.0x1098 = 0xfcc31c43 +48000000 OBJFE00.0x109c = 0x48000000 +00bfdd03 OBJFE00.0x10a0 = 0xbfdd03 +48014001 OBJFE00.0x10a4 = 0x48014001 +10c1dc43 OBJFE00.0x10a8 = 0x10c1dc43 +188e4001 OBJFE00.0x10ac = 0x188e4001 +80515c03 OBJFE00.0x10b0 = 0x80515c03 +48014001 OBJFE00.0x10b4 = 0x48014001 +90619c43 OBJFE00.0x10b8 = 0x90619c43 +48004001 OBJFE00.0x10bc = 0x48004001 +e00001e7 OBJFE00.0x10c0 = 0xe00001e7 +4003fffd OBJFE00.0x10c4 = 0x4003fffd +00001de7 OBJFE00.0x10c8 = 0x1de7 +80000000 OBJFE00.0x10cc = 0x80000000 +200446c0 OBJFE00.0x10d0 = 0x200446c0 +00000000 OBJFE00.0x10d4 = 0 +0800ffd0 OBJFE00.0x10d8 = 0x800ffd0 +00000006 OBJFE00.0x10dc = 0x6 +00000000 OBJFE00.0x10e0 = 0 +200145a6 OBJFE00.0x10e4 = 0x200145a6 +00000001 OBJFE00.0x10e8 = 0x1 +200446c0 OBJFE00.0x10ec = 0x200446c0 +00000000 OBJFE00.0x10f0 = 0 +0800ffd0 OBJFE00.0x10f4 = 0x800ffd0 +00000007 OBJFE00.0x10f8 = 0x7 +00000000 OBJFE00.0x10fc = 0 +200348e0 OBJFE00.0x1100 = 0x200348e0 +00010000 OBJFE00.0x1104 = 0x10000 +00000001 OBJFE00.0x1108 = 0x1 +00002200 OBJFE00.0x110c = 0x2200 +200148e3 OBJFE00.0x1110 = 0x200148e3 +00000000 OBJFE00.0x1114 = 0 +609a48e4 OBJFE00.0x1118 = 0x609a48e4 +00005de4 OBJFE00.0x111c = 0x5de4 +28004404 OBJFE00.0x1120 = 0x28004404 +9400dc04 OBJFE00.0x1124 = 0x9400dc04 +2c000000 OBJFE00.0x1128 = 0x2c000000 +98011c04 OBJFE00.0x112c = 0x98011c04 +2c000000 OBJFE00.0x1130 = 0x2c000000 +c0000007 OBJFE00.0x1134 = 0xc0000007 +60000002 OBJFE00.0x1138 = 0x60000002 +fc31dc03 OBJFE00.0x113c = 0xfc31dc03 +190e0000 OBJFE00.0x1140 = 0x190e0000 +200021e7 OBJFE00.0x1144 = 0x200021e7 +40000002 OBJFE00.0x1148 = 0x40000002 +e0001de4 OBJFE00.0x114c = 0xe0001de4 +28004000 OBJFE00.0x1150 = 0x28004000 +fc43dc03 OBJFE00.0x1154 = 0xfc43dc03 +1a8e0000 OBJFE00.0x1158 = 0x1a8e0000 +84009c04 OBJFE00.0x115c = 0x84009c04 +2c000000 OBJFE00.0x1160 = 0x2c000000 +7c001c23 OBJFE00.0x1164 = 0x7c001c23 +7000c004 OBJFE00.0x1168 = 0x7000c004 +000005f4 OBJFE00.0x116c = 0x5f4 +40000000 OBJFE00.0x1170 = 0x40000000 +e02fde03 OBJFE00.0x1174 = 0xe02fde03 +48014000 OBJFE00.0x1178 = 0x48014000 +fc03dc43 OBJFE00.0x117c = 0xfc03dc43 +198e0000 OBJFE00.0x1180 = 0x198e0000 +000005f4 OBJFE00.0x1184 = 0x5f4 +40000000 OBJFE00.0x1188 = 0x40000000 +88015c04 OBJFE00.0x118c = 0x88015c04 +2c000000 OBJFE00.0x1190 = 0x2c000000 +fc53dc03 OBJFE00.0x1194 = 0xfc53dc03 +1a8e0000 OBJFE00.0x1198 = 0x1a8e0000 +000005f4 OBJFE00.0x119c = 0x5f4 +40000000 OBJFE00.0x11a0 = 0x40000000 +a0219c03 OBJFE00.0x11a4 = 0xa0219c03 +48014000 OBJFE00.0x11a8 = 0x48014000 +b3f1dc43 OBJFE00.0x11ac = 0xb3f1dc43 +48004000 OBJFE00.0x11b0 = 0x48004000 +80221c03 OBJFE00.0x11b4 = 0x80221c03 +48014000 OBJFE00.0x11b8 = 0x48014000 +00615c05 OBJFE00.0x11bc = 0x615c05 +84000000 OBJFE00.0x11c0 = 0x84000000 +93f25c43 OBJFE00.0x11c4 = 0x93f25c43 +48004000 OBJFE00.0x11c8 = 0x48004000 +00815c15 OBJFE00.0x11cc = 0x815c15 +94000000 OBJFE00.0x11d0 = 0x94000000 +e0001de4 OBJFE00.0x11d4 = 0xe0001de4 +28004000 OBJFE00.0x11d8 = 0x28004000 +84009c04 OBJFE00.0x11dc = 0x84009c04 +2c000000 OBJFE00.0x11e0 = 0x2c000000 +7c001c33 OBJFE00.0x11e4 = 0x7c001c33 +7000c004 OBJFE00.0x11e8 = 0x7000c004 +60000007 OBJFE00.0x11ec = 0x60000007 +60000003 OBJFE00.0x11f0 = 0x60000003 +c00021e7 OBJFE00.0x11f4 = 0xc00021e7 +40000002 OBJFE00.0x11f8 = 0x40000002 +c0015de4 OBJFE00.0x11fc = 0xc0015de4 +28004000 OBJFE00.0x1200 = 0x28004000 +fc41dc03 OBJFE00.0x1204 = 0xfc41dc03 +1a8e0000 OBJFE00.0x1208 = 0x1a8e0000 +e0521d03 OBJFE00.0x120c = 0xe0521d03 +48014000 OBJFE00.0x1210 = 0x48014000 +d0015e43 OBJFE00.0x1214 = 0xd0015e43 +48004000 OBJFE00.0x1218 = 0x48004000 +0c825c03 OBJFE00.0x121c = 0xc825c03 +6800c000 OBJFE00.0x1220 = 0x6800c000 +000001f4 OBJFE00.0x1224 = 0x1f4 +40000000 OBJFE00.0x1228 = 0x40000000 +089fdd03 OBJFE00.0x122c = 0x89fdd03 +48010000 OBJFE00.0x1230 = 0x48010000 +fff1dc43 OBJFE00.0x1234 = 0xfff1dc43 +198e0000 OBJFE00.0x1238 = 0x198e0000 +000001f4 OBJFE00.0x123c = 0x1f4 +40000000 OBJFE00.0x1240 = 0x40000000 +88019c04 OBJFE00.0x1244 = 0x88019c04 +2c000000 OBJFE00.0x1248 = 0x2c000000 +fc61dc03 OBJFE00.0x124c = 0xfc61dc03 +1a8e0000 OBJFE00.0x1250 = 0x1a8e0000 +000001f4 OBJFE00.0x1254 = 0x1f4 +40000000 OBJFE00.0x1258 = 0x40000000 +c0919e03 OBJFE00.0x125c = 0xc0919e03 +48014000 OBJFE00.0x1260 = 0x48014000 +d3f1de43 OBJFE00.0x1264 = 0xd3f1de43 +48004000 OBJFE00.0x1268 = 0x48004000 +18229c03 OBJFE00.0x126c = 0x18229c03 +48010000 OBJFE00.0x1270 = 0x48010000 +1ff2dc43 OBJFE00.0x1274 = 0x1ff2dc43 +48000000 OBJFE00.0x1278 = 0x48000000 +a0a19c03 OBJFE00.0x127c = 0xa0a19c03 +48014000 OBJFE00.0x1280 = 0x48014000 +b0b1dc43 OBJFE00.0x1284 = 0xb0b1dc43 +48004000 OBJFE00.0x1288 = 0x48004000 +80a29c03 OBJFE00.0x128c = 0x80a29c03 +48014000 OBJFE00.0x1290 = 0x48014000 +0061dc05 OBJFE00.0x1294 = 0x61dc05 +84000000 OBJFE00.0x1298 = 0x84000000 +90b2dc43 OBJFE00.0x129c = 0x90b2dc43 +48004000 OBJFE00.0x12a0 = 0x48004000 +00a1dc15 OBJFE00.0x12a4 = 0xa1dc15 +94000000 OBJFE00.0x12a8 = 0x94000000 +c0015de4 OBJFE00.0x12ac = 0xc0015de4 +28004000 OBJFE00.0x12b0 = 0x28004000 +e0521d03 OBJFE00.0x12b4 = 0xe0521d03 +48014000 OBJFE00.0x12b8 = 0x48014000 +d0015e43 OBJFE00.0x12bc = 0xd0015e43 +48004000 OBJFE00.0x12c0 = 0x48004000 +0c825c13 OBJFE00.0x12c4 = 0xc825c13 +6800c000 OBJFE00.0x12c8 = 0x6800c000 +5040dc03 OBJFE00.0x12cc = 0x5040dc03 +20064000 OBJFE00.0x12d0 = 0x20064000 +20309c03 OBJFE00.0x12d4 = 0x20309c03 +20054000 OBJFE00.0x12d8 = 0x20054000 +fff0dc43 OBJFE00.0x12dc = 0xfff0dc43 +48000000 OBJFE00.0x12e0 = 0x48000000 +24811d03 OBJFE00.0x12e4 = 0x24811d03 +48010000 OBJFE00.0x12e8 = 0x48010000 +08219c03 OBJFE00.0x12ec = 0x8219c03 +6000c000 OBJFE00.0x12f0 = 0x6000c000 +7821dc03 OBJFE00.0x12f4 = 0x7821dc03 +5800c000 OBJFE00.0x12f8 = 0x5800c000 +fc509d43 OBJFE00.0x12fc = 0xfc509d43 +48000000 OBJFE00.0x1300 = 0x48000000 +106fdd03 OBJFE00.0x1304 = 0x106fdd03 +48010000 OBJFE00.0x1308 = 0x48010000 +1c315c43 OBJFE00.0x130c = 0x1c315c43 +40000000 OBJFE00.0x1310 = 0x40000000 +0851dc43 OBJFE00.0x1314 = 0x851dc43 +1b0e0000 OBJFE00.0x1318 = 0x1b0e0000 +600081e7 OBJFE00.0x131c = 0x600081e7 +40000001 OBJFE00.0x1320 = 0x40000001 +e00121e4 OBJFE00.0x1324 = 0xe00121e4 +28004000 OBJFE00.0x1328 = 0x28004000 +a040a003 OBJFE00.0x132c = 0xa040a003 +48014000 OBJFE00.0x1330 = 0x48014000 +b000e043 OBJFE00.0x1334 = 0xb000e043 +48004000 OBJFE00.0x1338 = 0x48004000 +0860a003 OBJFE00.0x133c = 0x860a003 +48010000 OBJFE00.0x1340 = 0x48010000 +0c50e043 OBJFE00.0x1344 = 0xc50e043 +48000000 OBJFE00.0x1348 = 0x48000000 +80412003 OBJFE00.0x134c = 0x80412003 +48014000 OBJFE00.0x1350 = 0x48014000 +0020a085 OBJFE00.0x1354 = 0x20a085 +84000000 OBJFE00.0x1358 = 0x84000000 +90002043 OBJFE00.0x135c = 0x90002043 +48004000 OBJFE00.0x1360 = 0x48004000 +10612003 OBJFE00.0x1364 = 0x10612003 +48010000 OBJFE00.0x1368 = 0x48010000 +00516043 OBJFE00.0x136c = 0x516043 +48000000 OBJFE00.0x1370 = 0x48000000 +0040a085 OBJFE00.0x1374 = 0x40a085 +94000000 OBJFE00.0x1378 = 0x94000000 +00001de7 OBJFE00.0x137c = 0x1de7 +80000000 OBJFE00.0x1380 = 0x80000000 +200446c0 OBJFE00.0x1384 = 0x200446c0 +00000000 OBJFE00.0x1388 = 0 +0800ffd0 OBJFE00.0x138c = 0x800ffd0 +00000008 OBJFE00.0x1390 = 0x8 +00000000 OBJFE00.0x1394 = 0 +200145a6 OBJFE00.0x1398 = 0x200145a6 +00000001 OBJFE00.0x139c = 0x1 +200446c0 OBJFE00.0x13a0 = 0x200446c0 +00000000 OBJFE00.0x13a4 = 0 +0800ffd0 OBJFE00.0x13a8 = 0x800ffd0 +00000009 OBJFE00.0x13ac = 0x9 +00000000 OBJFE00.0x13b0 = 0 +200348e0 OBJFE00.0x13b4 = 0x200348e0 +00010000 OBJFE00.0x13b8 = 0x10000 +00000001 OBJFE00.0x13bc = 0x1 +00002000 OBJFE00.0x13c0 = 0x2000 +200148e3 OBJFE00.0x13c4 = 0x200148e3 +00000000 OBJFE00.0x13c8 = 0 +607c48e4 OBJFE00.0x13cc = 0x607c48e4 +00005de4 OBJFE00.0x13d0 = 0x5de4 +28004404 OBJFE00.0x13d4 = 0x28004404 +9400dc04 OBJFE00.0x13d8 = 0x9400dc04 +2c000000 OBJFE00.0x13dc = 0x2c000000 +98009c04 OBJFE00.0x13e0 = 0x98009c04 +2c000000 OBJFE00.0x13e4 = 0x2c000000 +20000007 OBJFE00.0x13e8 = 0x20000007 +60000002 OBJFE00.0x13ec = 0x60000002 +fc31dc03 OBJFE00.0x13f0 = 0xfc31dc03 +190e0000 OBJFE00.0x13f4 = 0x190e0000 +c00021e7 OBJFE00.0x13f8 = 0xc00021e7 +40000001 OBJFE00.0x13fc = 0x40000001 +fc23dc03 OBJFE00.0x1400 = 0xfc23dc03 +1a8e0000 OBJFE00.0x1404 = 0x1a8e0000 +84001c04 OBJFE00.0x1408 = 0x84001c04 +2c000000 OBJFE00.0x140c = 0x2c000000 +000005f4 OBJFE00.0x1410 = 0x5f4 +40000000 OBJFE00.0x1414 = 0x40000000 +d003dc03 OBJFE00.0x1418 = 0xd003dc03 +1b0e4000 OBJFE00.0x141c = 0x1b0e4000 +000005f4 OBJFE00.0x1420 = 0x5f4 +40000000 OBJFE00.0x1424 = 0x40000000 +88011c04 OBJFE00.0x1428 = 0x88011c04 +2c000000 OBJFE00.0x142c = 0x2c000000 +fc43dc03 OBJFE00.0x1430 = 0xfc43dc03 +1a8e0000 OBJFE00.0x1434 = 0x1a8e0000 +000005f4 OBJFE00.0x1438 = 0x5f4 +40000000 OBJFE00.0x143c = 0x40000000 +a0011c03 OBJFE00.0x1440 = 0xa0011c03 +48014000 OBJFE00.0x1444 = 0x48014000 +b3f15c43 OBJFE00.0x1448 = 0xb3f15c43 +48004000 OBJFE00.0x144c = 0x48004000 +80019c03 OBJFE00.0x1450 = 0x80019c03 +48014000 OBJFE00.0x1454 = 0x48014000 +00411c05 OBJFE00.0x1458 = 0x411c05 +84000000 OBJFE00.0x145c = 0x84000000 +93f1dc43 OBJFE00.0x1460 = 0x93f1dc43 +48004000 OBJFE00.0x1464 = 0x48004000 +00611c15 OBJFE00.0x1468 = 0x611c15 +94000000 OBJFE00.0x146c = 0x94000000 +84001c14 OBJFE00.0x1470 = 0x84001c14 +2c000000 OBJFE00.0x1474 = 0x2c000000 +c0000007 OBJFE00.0x1478 = 0xc0000007 +60000002 OBJFE00.0x147c = 0x60000002 +400021e7 OBJFE00.0x1480 = 0x400021e7 +40000002 OBJFE00.0x1484 = 0x40000002 +c0011de4 OBJFE00.0x1488 = 0xc0011de4 +28004000 OBJFE00.0x148c = 0x28004000 +fc21dc03 OBJFE00.0x1490 = 0xfc21dc03 +1a8e0000 OBJFE00.0x1494 = 0x1a8e0000 +d0411d03 OBJFE00.0x1498 = 0xd0411d03 +48004000 OBJFE00.0x149c = 0x48004000 +0c415c03 OBJFE00.0x14a0 = 0xc415c03 +6800c000 OBJFE00.0x14a4 = 0x6800c000 +000001f4 OBJFE00.0x14a8 = 0x1f4 +40000000 OBJFE00.0x14ac = 0x40000000 +0051dc03 OBJFE00.0x14b0 = 0x51dc03 +198e0000 OBJFE00.0x14b4 = 0x198e0000 +000001f4 OBJFE00.0x14b8 = 0x1f4 +40000000 OBJFE00.0x14bc = 0x40000000 +88019c04 OBJFE00.0x14c0 = 0x88019c04 +2c000000 OBJFE00.0x14c4 = 0x2c000000 +fc61dc03 OBJFE00.0x14c8 = 0xfc61dc03 +1a8e0000 OBJFE00.0x14cc = 0x1a8e0000 +000001f4 OBJFE00.0x14d0 = 0x1f4 +40000000 OBJFE00.0x14d4 = 0x40000000 +c0519e03 OBJFE00.0x14d8 = 0xc0519e03 +48004000 OBJFE00.0x14dc = 0x48004000 +0061dc03 OBJFE00.0x14e0 = 0x61dc03 +48000000 OBJFE00.0x14e4 = 0x48000000 +a0721c03 OBJFE00.0x14e8 = 0xa0721c03 +48014000 OBJFE00.0x14ec = 0x48014000 +b3f25c43 OBJFE00.0x14f0 = 0xb3f25c43 +48004000 OBJFE00.0x14f4 = 0x48004000 +80729c03 OBJFE00.0x14f8 = 0x80729c03 +48014000 OBJFE00.0x14fc = 0x48014000 +00819c05 OBJFE00.0x1500 = 0x819c05 +84000000 OBJFE00.0x1504 = 0x84000000 +93f2dc43 OBJFE00.0x1508 = 0x93f2dc43 +48004000 OBJFE00.0x150c = 0x48004000 +00a19c15 OBJFE00.0x1510 = 0xa19c15 +94000000 OBJFE00.0x1514 = 0x94000000 +c0011de4 OBJFE00.0x1518 = 0xc0011de4 +28004000 OBJFE00.0x151c = 0x28004000 +d0411d03 OBJFE00.0x1520 = 0xd0411d03 +48004000 OBJFE00.0x1524 = 0x48004000 +0c415c13 OBJFE00.0x1528 = 0xc415c13 +6800c000 OBJFE00.0x152c = 0x6800c000 +50209c03 OBJFE00.0x1530 = 0x50209c03 +20064000 OBJFE00.0x1534 = 0x20064000 +20201c03 OBJFE00.0x1538 = 0x20201c03 +20004000 OBJFE00.0x153c = 0x20004000 +14409d03 OBJFE00.0x1540 = 0x14409d03 +48000000 OBJFE00.0x1544 = 0x48000000 +08001c03 OBJFE00.0x1548 = 0x8001c03 +6000c000 OBJFE00.0x154c = 0x6000c000 +0801dc03 OBJFE00.0x1550 = 0x801dc03 +1b0e0000 OBJFE00.0x1554 = 0x1b0e0000 +600081e7 OBJFE00.0x1558 = 0x600081e7 +40000001 OBJFE00.0x155c = 0x40000001 +d00121e4 OBJFE00.0x1560 = 0xd00121e4 +28004000 OBJFE00.0x1564 = 0x28004000 +a040a003 OBJFE00.0x1568 = 0xa040a003 +48014000 OBJFE00.0x156c = 0x48014000 +b3f0e043 OBJFE00.0x1570 = 0xb3f0e043 +48004000 OBJFE00.0x1574 = 0x48004000 +0800a003 OBJFE00.0x1578 = 0x800a003 +48010000 OBJFE00.0x157c = 0x48010000 +0ff0e043 OBJFE00.0x1580 = 0xff0e043 +48000000 OBJFE00.0x1584 = 0x48000000 +80412003 OBJFE00.0x1588 = 0x80412003 +48014000 OBJFE00.0x158c = 0x48014000 +0020a085 OBJFE00.0x1590 = 0x20a085 +84000000 OBJFE00.0x1594 = 0x84000000 +93f16043 OBJFE00.0x1598 = 0x93f16043 +48004000 OBJFE00.0x159c = 0x48004000 +10012003 OBJFE00.0x15a0 = 0x10012003 +48010000 OBJFE00.0x15a4 = 0x48010000 +17f16043 OBJFE00.0x15a8 = 0x17f16043 +48000000 OBJFE00.0x15ac = 0x48000000 +0040a085 OBJFE00.0x15b0 = 0x40a085 +94000000 OBJFE00.0x15b4 = 0x94000000 +00001de7 OBJFE00.0x15b8 = 0x1de7 +80000000 OBJFE00.0x15bc = 0x80000000 +200446c0 OBJFE00.0x15c0 = 0x200446c0 +00000000 OBJFE00.0x15c4 = 0 +0800ffd0 OBJFE00.0x15c8 = 0x800ffd0 +0000000a OBJFE00.0x15cc = 0xa +00000000 OBJFE00.0x15d0 = 0 +200145a6 OBJFE00.0x15d4 = 0x200145a6 +00000001 OBJFE00.0x15d8 = 0x1 +200446c0 OBJFE00.0x15dc = 0x200446c0 +00000000 OBJFE00.0x15e0 = 0 +0800ffd0 OBJFE00.0x15e4 = 0x800ffd0 +0000000b OBJFE00.0x15e8 = 0xb +00000000 OBJFE00.0x15ec = 0 +200348e0 OBJFE00.0x15f0 = 0x200348e0 +00010000 OBJFE00.0x15f4 = 0x10000 +00000001 OBJFE00.0x15f8 = 0x1 +00001f00 OBJFE00.0x15fc = 0x1f00 +200148e3 OBJFE00.0x1600 = 0x200148e3 +00000000 OBJFE00.0x1604 = 0 +603648e4 OBJFE00.0x1608 = 0x603648e4 +00005de4 OBJFE00.0x160c = 0x5de4 +28004404 OBJFE00.0x1610 = 0x28004404 +94009c04 OBJFE00.0x1614 = 0x94009c04 +2c000000 OBJFE00.0x1618 = 0x2c000000 +98001c04 OBJFE00.0x161c = 0x98001c04 +2c000000 OBJFE00.0x1620 = 0x2c000000 +e000dde4 OBJFE00.0x1624 = 0xe000dde4 +28004000 OBJFE00.0x1628 = 0x28004000 +50001c03 OBJFE00.0x162c = 0x50001c03 +20044000 OBJFE00.0x1630 = 0x20044000 +7c309c23 OBJFE00.0x1634 = 0x7c309c23 +7000c004 OBJFE00.0x1638 = 0x7000c004 +2000dd03 OBJFE00.0x163c = 0x2000dd03 +20074000 OBJFE00.0x1640 = 0x20074000 +84001c04 OBJFE00.0x1644 = 0x84001c04 +2c000000 OBJFE00.0x1648 = 0x2c000000 +0bf09d43 OBJFE00.0x164c = 0xbf09d43 +48000000 OBJFE00.0x1650 = 0x48000000 +0c001c03 OBJFE00.0x1654 = 0xc001c03 +48010000 OBJFE00.0x1658 = 0x48010000 +0bf09c43 OBJFE00.0x165c = 0xbf09c43 +48000000 OBJFE00.0x1660 = 0x48000000 +7800dc03 OBJFE00.0x1664 = 0x7800dc03 +5800c000 OBJFE00.0x1668 = 0x5800c000 +08011c03 OBJFE00.0x166c = 0x8011c03 +6000c000 OBJFE00.0x1670 = 0x6000c000 +d0001de4 OBJFE00.0x1674 = 0xd0001de4 +28004000 OBJFE00.0x1678 = 0x28004000 +0c215c43 OBJFE00.0x167c = 0xc215c43 +40000000 OBJFE00.0x1680 = 0x40000000 +c04fde03 OBJFE00.0x1684 = 0xc04fde03 +48014000 OBJFE00.0x1688 = 0x48014000 +1401dc63 OBJFE00.0x168c = 0x1401dc63 +1a0e0000 OBJFE00.0x1690 = 0x1a0e0000 +fc4fdd03 OBJFE00.0x1694 = 0xfc4fdd03 +48010000 OBJFE00.0x1698 = 0x48010000 +fc51dc63 OBJFE00.0x169c = 0xfc51dc63 +1b000000 OBJFE00.0x16a0 = 0x1b000000 +c000a1e7 OBJFE00.0x16a4 = 0xc000a1e7 +40000000 OBJFE00.0x16a8 = 0x40000000 +a0408003 OBJFE00.0x16ac = 0xa0408003 +48014000 OBJFE00.0x16b0 = 0x48014000 +b050c043 OBJFE00.0x16b4 = 0xb050c043 +48004000 OBJFE00.0x16b8 = 0x48004000 +80410003 OBJFE00.0x16bc = 0x80410003 +48014000 OBJFE00.0x16c0 = 0x48014000 +00200085 OBJFE00.0x16c4 = 0x200085 +84000000 OBJFE00.0x16c8 = 0x84000000 +90514043 OBJFE00.0x16cc = 0x90514043 +48004000 OBJFE00.0x16d0 = 0x48004000 +00400085 OBJFE00.0x16d4 = 0x400085 +94000000 OBJFE00.0x16d8 = 0x94000000 +00001de7 OBJFE00.0x16dc = 0x1de7 +80000000 OBJFE00.0x16e0 = 0x80000000 +200446c0 OBJFE00.0x16e4 = 0x200446c0 +00000000 OBJFE00.0x16e8 = 0 +0800ffd0 OBJFE00.0x16ec = 0x800ffd0 +0000000c OBJFE00.0x16f0 = 0xc +00000000 OBJFE00.0x16f4 = 0 +200145a6 OBJFE00.0x16f8 = 0x200145a6 +00000001 OBJFE00.0x16fc = 0x1 +200446c0 OBJFE00.0x1700 = 0x200446c0 +00000000 OBJFE00.0x1704 = 0 +0800ffd0 OBJFE00.0x1708 = 0x800ffd0 +0000000d OBJFE00.0x170c = 0xd +00000000 OBJFE00.0x1710 = 0 +200348e0 OBJFE00.0x1714 = 0x200348e0 +00010000 OBJFE00.0x1718 = 0x10000 +00000001 OBJFE00.0x171c = 0x1 +00001e00 OBJFE00.0x1720 = 0x1e00 +200148e3 OBJFE00.0x1724 = 0x200148e3 +00000000 OBJFE00.0x1728 = 0 +602848e4 OBJFE00.0x172c = 0x602848e4 +00005de4 OBJFE00.0x1730 = 0x5de4 +28004404 OBJFE00.0x1734 = 0x28004404 +94009c04 OBJFE00.0x1738 = 0x94009c04 +2c000000 OBJFE00.0x173c = 0x2c000000 +98001c04 OBJFE00.0x1740 = 0x98001c04 +2c000000 OBJFE00.0x1744 = 0x2c000000 +2000dde4 OBJFE00.0x1748 = 0x2000dde4 +28004000 OBJFE00.0x174c = 0x28004000 +50001c03 OBJFE00.0x1750 = 0x50001c03 +20044000 OBJFE00.0x1754 = 0x20044000 +84009c04 OBJFE00.0x1758 = 0x84009c04 +2c000000 OBJFE00.0x175c = 0x2c000000 +d0301d03 OBJFE00.0x1760 = 0xd0301d03 +20008000 OBJFE00.0x1764 = 0x20008000 +08001c03 OBJFE00.0x1768 = 0x8001c03 +48000000 OBJFE00.0x176c = 0x48000000 +08001c03 OBJFE00.0x1770 = 0x8001c03 +6000c000 OBJFE00.0x1774 = 0x6000c000 +c001dc23 OBJFE00.0x1778 = 0xc001dc23 +188e4000 OBJFE00.0x177c = 0x188e4000 +fc01dc23 OBJFE00.0x1780 = 0xfc01dc23 +1b000000 OBJFE00.0x1784 = 0x1b000000 +e000a1e7 OBJFE00.0x1788 = 0xe000a1e7 +40000000 OBJFE00.0x178c = 0x40000000 +7c00c023 OBJFE00.0x1790 = 0x7c00c023 +7000c004 OBJFE00.0x1794 = 0x7000c004 +a0010003 OBJFE00.0x1798 = 0xa0010003 +48014000 OBJFE00.0x179c = 0x48014000 +b0314043 OBJFE00.0x17a0 = 0xb0314043 +48004000 OBJFE00.0x17a4 = 0x48004000 +80018003 OBJFE00.0x17a8 = 0x80018003 +48014000 OBJFE00.0x17ac = 0x48014000 +00408085 OBJFE00.0x17b0 = 0x408085 +84000000 OBJFE00.0x17b4 = 0x84000000 +9031c043 OBJFE00.0x17b8 = 0x9031c043 +48004000 OBJFE00.0x17bc = 0x48004000 +00608085 OBJFE00.0x17c0 = 0x608085 +94000000 OBJFE00.0x17c4 = 0x94000000 +00001de7 OBJFE00.0x17c8 = 0x1de7 +80000000 OBJFE00.0x17cc = 0x80000000 +200446c0 OBJFE00.0x17d0 = 0x200446c0 +00000000 OBJFE00.0x17d4 = 0 +0800ffd0 OBJFE00.0x17d8 = 0x800ffd0 +0000000e OBJFE00.0x17dc = 0xe +00000000 OBJFE00.0x17e0 = 0 +# out of band: 00000068 08103fac +# out of band: 0000006c 0000d200 +200145a6 OBJFE00.0x17e4 = 0x200145a6 +00000001 OBJFE00.0x17e8 = 0x1 +200446c0 OBJFE00.0x17ec = 0x200446c0 +00000000 OBJFE00.0x17f0 = 0 +0800ffd0 OBJFE00.0x17f4 = 0x800ffd0 +0000000f OBJFE00.0x17f8 = 0xf +00000000 OBJFE00.0x17fc = 0 +# out of band: 00000070 0810407c +# out of band: 00000074 00001e00 +200348e0 OBJFE00.0x1800 = 0x200348e0 +00010000 OBJFE00.0x1804 = 0x10000 +00000001 OBJFE00.0x1808 = 0x1 +00001900 OBJFE00.0x180c = 0x1900 +200148e3 OBJFE00.0x1810 = 0x200148e3 +00000000 OBJFE00.0x1814 = 0 +610448e4 OBJFE00.0x1818 = 0x610448e4 +00005de4 OBJFE00.0x181c = 0x5de4 +28004404 OBJFE00.0x1820 = 0x28004404 +98025c04 OBJFE00.0x1824 = 0x98025c04 +2c000000 OBJFE00.0x1828 = 0x2c000000 +94011c04 OBJFE00.0x182c = 0x94011c04 +2c000000 OBJFE00.0x1830 = 0x2c000000 +84031c04 OBJFE00.0x1834 = 0x84031c04 +2c000000 OBJFE00.0x1838 = 0x2c000000 +20919c03 OBJFE00.0x183c = 0x20919c03 +50014001 OBJFE00.0x1840 = 0x50014001 +20409c03 OBJFE00.0x1844 = 0x20409c03 +20184000 OBJFE00.0x1848 = 0x20184000 +20901c43 OBJFE00.0x184c = 0x20901c43 +20ff4001 OBJFE00.0x1850 = 0x20ff4001 +23f15c03 OBJFE00.0x1854 = 0x23f15c03 +20804001 OBJFE00.0x1858 = 0x20804001 +0091dc03 OBJFE00.0x185c = 0x91dc03 +50014001 OBJFE00.0x1860 = 0x50014001 +30915c03 OBJFE00.0x1864 = 0x30915c03 +200a4001 OBJFE00.0x1868 = 0x200a4001 +00901c43 OBJFE00.0x186c = 0x901c43 +20ff4001 OBJFE00.0x1870 = 0x20ff4001 +03f01c03 OBJFE00.0x1874 = 0x3f01c03 +20804001 OBJFE00.0x1878 = 0x20804001 +4020dd03 OBJFE00.0x187c = 0x4020dd03 +48014001 OBJFE00.0x1880 = 0x48014001 +10901c03 OBJFE00.0x1884 = 0x10901c03 +20004001 OBJFE00.0x1888 = 0x20004001 +53f09d43 OBJFE00.0x188c = 0x53f09d43 +48004001 OBJFE00.0x1890 = 0x48004001 +a062dc03 OBJFE00.0x1894 = 0xa062dc03 +48014000 OBJFE00.0x1898 = 0x48014000 +b0529c43 OBJFE00.0x189c = 0xb0529c43 +48004000 OBJFE00.0x18a0 = 0x48004000 +8071dc03 OBJFE00.0x18a4 = 0x8071dc03 +48014000 OBJFE00.0x18a8 = 0x48014000 +0c719c03 OBJFE00.0x18ac = 0xc719c03 +6800c000 OBJFE00.0x18b0 = 0x6800c000 +03f15c04 OBJFE00.0x18b4 = 0x3f15c04 +3000c3c0 OBJFE00.0x18b8 = 0x3000c3c0 +10619e03 OBJFE00.0x18bc = 0x10619e03 +4800c000 OBJFE00.0x18c0 = 0x4800c000 +0c619c03 OBJFE00.0x18c4 = 0xc619c03 +6800c000 OBJFE00.0x18c8 = 0x6800c000 +c0619e03 OBJFE00.0x18cc = 0xc0619e03 +48014000 OBJFE00.0x18d0 = 0x48014000 +d3f21e43 OBJFE00.0x18d4 = 0xd3f21e43 +48004000 OBJFE00.0x18d8 = 0x48004000 +08619c03 OBJFE00.0x18dc = 0x8619c03 +5800c000 OBJFE00.0x18e0 = 0x5800c000 +18819fc3 OBJFE00.0x18e4 = 0x18819fc3 +40000000 OBJFE00.0x18e8 = 0x40000000 +08821c03 OBJFE00.0x18ec = 0x8821c03 +5800c000 OBJFE00.0x18f0 = 0x5800c000 +183fdd03 OBJFE00.0x18f4 = 0x183fdd03 +48010000 OBJFE00.0x18f8 = 0x48010000 +d0019de4 OBJFE00.0x18fc = 0xd0019de4 +28004000 OBJFE00.0x1900 = 0x28004000 +2021dc63 OBJFE00.0x1904 = 0x2021dc63 +188e0000 OBJFE00.0x1908 = 0x188e0000 +fc3fdd03 OBJFE00.0x190c = 0xfc3fdd03 +48010000 OBJFE00.0x1910 = 0x48010000 +c0021de4 OBJFE00.0x1914 = 0xc0021de4 +28004000 OBJFE00.0x1918 = 0x28004000 +fc21dc63 OBJFE00.0x191c = 0xfc21dc63 +1b000000 OBJFE00.0x1920 = 0x1b000000 +0c8fdd03 OBJFE00.0x1924 = 0xc8fdd03 +4801c000 OBJFE00.0x1928 = 0x4801c000 +fc021de4 OBJFE00.0x192c = 0xfc021de4 +28000000 OBJFE00.0x1930 = 0x28000000 +fc61dc43 OBJFE00.0x1934 = 0xfc61dc43 +1a000000 OBJFE00.0x1938 = 0x1a000000 +00501c04 OBJFE00.0x193c = 0x501c04 +3400c3c0 OBJFE00.0x1940 = 0x3400c3c0 +90001c43 OBJFE00.0x1944 = 0x90001c43 +48004000 OBJFE00.0x1948 = 0x48004000 +c00021e7 OBJFE00.0x194c = 0xc00021e7 +40000004 OBJFE00.0x1950 = 0x40000004 +e09fdd03 OBJFE00.0x1954 = 0xe09fdd03 +48014000 OBJFE00.0x1958 = 0x48014000 +f3f1dc43 OBJFE00.0x195c = 0xf3f1dc43 +1b0e4000 OBJFE00.0x1960 = 0x1b0e4000 +000001e7 OBJFE00.0x1964 = 0x1e7 +80000000 OBJFE00.0x1968 = 0x80000000 +60011de4 OBJFE00.0x196c = 0x60011de4 +28004000 OBJFE00.0x1970 = 0x28004000 +78341c03 OBJFE00.0x1974 = 0x78341c03 +5800c000 OBJFE00.0x1978 = 0x5800c000 +08339c03 OBJFE00.0x197c = 0x8339c03 +6000c000 OBJFE00.0x1980 = 0x6000c000 +20431c03 OBJFE00.0x1984 = 0x20431c03 +50014001 OBJFE00.0x1988 = 0x50014001 +1c035de4 OBJFE00.0x198c = 0x1c035de4 +28000000 OBJFE00.0x1990 = 0x28000000 +40241c43 OBJFE00.0x1994 = 0x40241c43 +40000000 OBJFE00.0x1998 = 0x40000000 +20415c43 OBJFE00.0x199c = 0x20415c43 +20ff4001 OBJFE00.0x19a0 = 0x20ff4001 +23f15c03 OBJFE00.0x19a4 = 0x23f15c03 +208a4001 OBJFE00.0x19a8 = 0x208a4001 +00419c03 OBJFE00.0x19ac = 0x419c03 +50014001 OBJFE00.0x19b0 = 0x50014001 +0043dc43 OBJFE00.0x19b4 = 0x43dc43 +20ff4001 OBJFE00.0x19b8 = 0x20ff4001 +03f0dc03 OBJFE00.0x19bc = 0x3f0dc03 +209e4001 OBJFE00.0x19c0 = 0x209e4001 +3043dc03 OBJFE00.0x19c4 = 0x3043dc03 +200a4001 OBJFE00.0x19c8 = 0x200a4001 +10445c03 OBJFE00.0x19cc = 0x10445c03 +20064001 OBJFE00.0x19d0 = 0x20064001 +0cd09c03 OBJFE00.0x19d4 = 0xcd09c03 +6800c000 OBJFE00.0x19d8 = 0x6800c000 +18d35c03 OBJFE00.0x19dc = 0x18d35c03 +48000000 OBJFE00.0x19e0 = 0x48000000 +10209e03 OBJFE00.0x19e4 = 0x10209e03 +4800c000 OBJFE00.0x19e8 = 0x4800c000 +0c209c03 OBJFE00.0x19ec = 0xc209c03 +6800c000 OBJFE00.0x19f0 = 0x6800c000 +38211c03 OBJFE00.0x19f4 = 0x38211c03 +48010000 OBJFE00.0x19f8 = 0x48010000 +43f15c43 OBJFE00.0x19fc = 0x43f15c43 +48000000 OBJFE00.0x1a00 = 0x48000000 +2c409c03 OBJFE00.0x1a04 = 0x2c409c03 +48010000 OBJFE00.0x1a08 = 0x48010000 +2850dc43 OBJFE00.0x1a0c = 0x2850dc43 +48000000 OBJFE00.0x1a10 = 0x48000000 +60925c03 OBJFE00.0x1a14 = 0x60925c03 +48014000 OBJFE00.0x1a18 = 0x48014000 +0020dc85 OBJFE00.0x1a1c = 0x20dc85 +84000000 OBJFE00.0x1a20 = 0x84000000 +fc821c43 OBJFE00.0x1a24 = 0xfc821c43 +48000000 OBJFE00.0x1a28 = 0x48000000 +e09fdd03 OBJFE00.0x1a2c = 0xe09fdd03 +48014000 OBJFE00.0x1a30 = 0x48014000 +f081dc43 OBJFE00.0x1a34 = 0xf081dc43 +188e4000 OBJFE00.0x1a38 = 0x188e4000 +1c411c03 OBJFE00.0x1a3c = 0x1c411c03 +48010000 OBJFE00.0x1a40 = 0x48010000 +00515c43 OBJFE00.0x1a44 = 0x515c43 +48000000 OBJFE00.0x1a48 = 0x48000000 +2cc2dc03 OBJFE00.0x1a4c = 0x2cc2dc03 +48010000 OBJFE00.0x1a50 = 0x48010000 +28f29c43 OBJFE00.0x1a54 = 0x28f29c43 +48000000 OBJFE00.0x1a58 = 0x48000000 +1c61dc03 OBJFE00.0x1a5c = 0x1c61dc03 +48010000 OBJFE00.0x1a60 = 0x48010000 +01101c43 OBJFE00.0x1a64 = 0x1101c43 +48000000 OBJFE00.0x1a68 = 0x48000000 +0040dc85 OBJFE00.0x1a6c = 0x40dc85 +94000000 OBJFE00.0x1a70 = 0x94000000 +600001e7 OBJFE00.0x1a74 = 0x600001e7 +4003fffd OBJFE00.0x1a78 = 0x4003fffd +80001de7 OBJFE00.0x1a7c = 0x80001de7 +40000006 OBJFE00.0x1a80 = 0x40000006 +c0cfdd03 OBJFE00.0x1a84 = 0xc0cfdd03 +48014000 OBJFE00.0x1a88 = 0x48014000 +50009de4 OBJFE00.0x1a8c = 0x50009de4 +28004000 OBJFE00.0x1a90 = 0x28004000 +d3f1dc43 OBJFE00.0x1a94 = 0xd3f1dc43 +188e4000 OBJFE00.0x1a98 = 0x188e4000 +fc209c03 OBJFE00.0x1a9c = 0xfc209c03 +4800ffff OBJFE00.0x1aa0 = 0x4800ffff +0841dc03 OBJFE00.0x1aa4 = 0x841dc03 +19000000 OBJFE00.0x1aa8 = 0x19000000 +000021e7 OBJFE00.0x1aac = 0x21e7 +80000000 OBJFE00.0x1ab0 = 0x80000000 +e09fdd03 OBJFE00.0x1ab4 = 0xe09fdd03 +48014000 OBJFE00.0x1ab8 = 0x48014000 +f3f1dc43 OBJFE00.0x1abc = 0xf3f1dc43 +1b0e4000 OBJFE00.0x1ac0 = 0x1b0e4000 +000001e7 OBJFE00.0x1ac4 = 0x1e7 +80000000 OBJFE00.0x1ac8 = 0x80000000 +60011de4 OBJFE00.0x1acc = 0x60011de4 +28004000 OBJFE00.0x1ad0 = 0x28004000 +1c019de4 OBJFE00.0x1ad4 = 0x1c019de4 +28000000 OBJFE00.0x1ad8 = 0x28000000 +20435c03 OBJFE00.0x1adc = 0x20435c03 +50014001 OBJFE00.0x1ae0 = 0x50014001 +20409c43 OBJFE00.0x1ae4 = 0x20409c43 +20ff4001 OBJFE00.0x1ae8 = 0x20ff4001 +23f09c03 OBJFE00.0x1aec = 0x23f09c03 +20844001 OBJFE00.0x1af0 = 0x20844001 +0043dc03 OBJFE00.0x1af4 = 0x43dc03 +50014001 OBJFE00.0x1af8 = 0x50014001 +30439c03 OBJFE00.0x1afc = 0x30439c03 +20044001 OBJFE00.0x1b00 = 0x20044001 +0040dc43 OBJFE00.0x1b04 = 0x40dc43 +20ff4001 OBJFE00.0x1b08 = 0x20ff4001 +03f0dc03 OBJFE00.0x1b0c = 0x3f0dc03 +20864001 OBJFE00.0x1b10 = 0x20864001 +10441c03 OBJFE00.0x1b14 = 0x10441c03 +20064001 OBJFE00.0x1b18 = 0x20064001 +0c609c03 OBJFE00.0x1b1c = 0xc609c03 +6800c000 OBJFE00.0x1b20 = 0x6800c000 +10209e03 OBJFE00.0x1b24 = 0x10209e03 +4800c000 OBJFE00.0x1b28 = 0x4800c000 +0c209c03 OBJFE00.0x1b2c = 0xc209c03 +6800c000 OBJFE00.0x1b30 = 0x6800c000 +08c1dc03 OBJFE00.0x1b34 = 0x8c1dc03 +1b0e0000 OBJFE00.0x1b38 = 0x1b0e0000 +c00081e7 OBJFE00.0x1b3c = 0xc00081e7 +40000000 OBJFE00.0x1b40 = 0x40000000 +2cc12003 OBJFE00.0x1b44 = 0x2cc12003 +48010000 OBJFE00.0x1b48 = 0x48010000 +2bf16043 OBJFE00.0x1b4c = 0x2bf16043 +48000000 OBJFE00.0x1b50 = 0x48000000 +1cc0a003 OBJFE00.0x1b54 = 0x1cc0a003 +48010000 OBJFE00.0x1b58 = 0x48010000 +00412005 OBJFE00.0x1b5c = 0x412005 +84000000 OBJFE00.0x1b60 = 0x84000000 +03f0e043 OBJFE00.0x1b64 = 0x3f0e043 +48000000 OBJFE00.0x1b68 = 0x48000000 +00212005 OBJFE00.0x1b6c = 0x212005 +94000000 OBJFE00.0x1b70 = 0x94000000 +c0709c03 OBJFE00.0x1b74 = 0xc0709c03 +48004000 OBJFE00.0x1b78 = 0x48004000 +0c209c03 OBJFE00.0x1b7c = 0xc209c03 +6800c000 OBJFE00.0x1b80 = 0x6800c000 +08c1dc03 OBJFE00.0x1b84 = 0x8c1dc03 +1b0e0000 OBJFE00.0x1b88 = 0x1b0e0000 +000081e7 OBJFE00.0x1b8c = 0x81e7 +40000001 OBJFE00.0x1b90 = 0x40000001 +c0c0a203 OBJFE00.0x1b94 = 0xc0c0a203 +48014000 OBJFE00.0x1b98 = 0x48014000 +d3f0e243 OBJFE00.0x1b9c = 0xd3f0e243 +48004000 OBJFE00.0x1ba0 = 0x48004000 +2c212003 OBJFE00.0x1ba4 = 0x2c212003 +48010000 OBJFE00.0x1ba8 = 0x48010000 +28316043 OBJFE00.0x1bac = 0x28316043 +48000000 OBJFE00.0x1bb0 = 0x48000000 +1c20a003 OBJFE00.0x1bb4 = 0x1c20a003 +48010000 OBJFE00.0x1bb8 = 0x48010000 +fc412005 OBJFE00.0x1bbc = 0xfc412005 +87ffffff OBJFE00.0x1bc0 = 0x87ffffff +0030e043 OBJFE00.0x1bc4 = 0x30e043 +48000000 OBJFE00.0x1bc8 = 0x48000000 +fc212005 OBJFE00.0x1bcc = 0xfc212005 +97ffffff OBJFE00.0x1bd0 = 0x97ffffff +2cd2dc03 OBJFE00.0x1bd4 = 0x2cd2dc03 +48010000 OBJFE00.0x1bd8 = 0x48010000 +3c619c03 OBJFE00.0x1bdc = 0x3c619c03 +48000000 OBJFE00.0x1be0 = 0x48000000 +28e29c43 OBJFE00.0x1be4 = 0x28e29c43 +48000000 OBJFE00.0x1be8 = 0x48000000 +60925c03 OBJFE00.0x1bec = 0x60925c03 +48014000 OBJFE00.0x1bf0 = 0x48014000 +fc821c43 OBJFE00.0x1bf4 = 0xfc821c43 +48000000 OBJFE00.0x1bf8 = 0x48000000 +e09fdd03 OBJFE00.0x1bfc = 0xe09fdd03 +48014000 OBJFE00.0x1c00 = 0x48014000 +f081dc43 OBJFE00.0x1c04 = 0xf081dc43 +188e4000 OBJFE00.0x1c08 = 0x188e4000 +1cf1dc03 OBJFE00.0x1c0c = 0x1cf1dc03 +48010000 OBJFE00.0x1c10 = 0x48010000 +01001c43 OBJFE00.0x1c14 = 0x1001c43 +48000000 OBJFE00.0x1c18 = 0x48000000 +e00001e7 OBJFE00.0x1c1c = 0xe00001e7 +4003fffb OBJFE00.0x1c20 = 0x4003fffb +00001de7 OBJFE00.0x1c24 = 0x1de7 +80000000 OBJFE00.0x1c28 = 0x80000000 +200446c0 OBJFE00.0x1c2c = 0x200446c0 +00000000 OBJFE00.0x1c30 = 0 +0800ffd0 OBJFE00.0x1c34 = 0x800ffd0 +00000010 OBJFE00.0x1c38 = 0x10 +00000000 OBJFE00.0x1c3c = 0 +# out of band: 00000078 08104098 +# out of band: 0000007c 00044200 +200145a6 OBJFE00.0x1c40 = 0x200145a6 +00000001 OBJFE00.0x1c44 = 0x1 +200446c0 OBJFE00.0x1c48 = 0x200446c0 +00000000 OBJFE00.0x1c4c = 0 +0800ffd0 OBJFE00.0x1c50 = 0x800ffd0 +00000011 OBJFE00.0x1c54 = 0x11 +00000000 OBJFE00.0x1c58 = 0 +# out of band: 00000080 081044d8 +# out of band: 00000084 00001e00 +200348e0 OBJFE00.0x1c5c = 0x200348e0 +00010000 OBJFE00.0x1c60 = 0x10000 +00000001 OBJFE00.0x1c64 = 0x1 +00001800 OBJFE00.0x1c68 = 0x1800 +200148e3 OBJFE00.0x1c6c = 0x200148e3 +00000000 OBJFE00.0x1c70 = 0 +603848e4 OBJFE00.0x1c74 = 0x603848e4 +00005de4 OBJFE00.0x1c78 = 0x5de4 +28004404 OBJFE00.0x1c7c = 0x28004404 +94001c04 OBJFE00.0x1c80 = 0x94001c04 +2c000000 OBJFE00.0x1c84 = 0x2c000000 +84009c04 OBJFE00.0x1c88 = 0x84009c04 +2c000000 OBJFE00.0x1c8c = 0x2c000000 +f0011de4 OBJFE00.0x1c90 = 0xf0011de4 +28004000 OBJFE00.0x1c94 = 0x28004000 +20001c03 OBJFE00.0x1c98 = 0x20001c03 +20044000 OBJFE00.0x1c9c = 0x20044000 +40009d03 OBJFE00.0x1ca0 = 0x40009d03 +48014001 OBJFE00.0x1ca4 = 0x48014001 +d0001de4 OBJFE00.0x1ca8 = 0xd0001de4 +28004000 OBJFE00.0x1cac = 0x28004000 +53f0dd43 OBJFE00.0x1cb0 = 0x53f0dd43 +48004001 OBJFE00.0x1cb4 = 0x48004001 +c02fde03 OBJFE00.0x1cb8 = 0xc02fde03 +48014000 OBJFE00.0x1cbc = 0x48014000 +0c01dc43 OBJFE00.0x1cc0 = 0xc01dc43 +1a0e0000 OBJFE00.0x1cc4 = 0x1a0e0000 +fc2fdd03 OBJFE00.0x1cc8 = 0xfc2fdd03 +48010000 OBJFE00.0x1ccc = 0x48010000 +98001c04 OBJFE00.0x1cd0 = 0x98001c04 +2c000000 OBJFE00.0x1cd4 = 0x2c000000 +fc31dc63 OBJFE00.0x1cd8 = 0xfc31dc63 +1b000000 OBJFE00.0x1cdc = 0x1b000000 +e00fde03 OBJFE00.0x1ce0 = 0xe00fde03 +48014000 OBJFE00.0x1ce4 = 0x48014000 +fc41dc43 OBJFE00.0x1ce8 = 0xfc41dc43 +1a000000 OBJFE00.0x1cec = 0x1a000000 +6000a1e7 OBJFE00.0x1cf0 = 0x6000a1e7 +40000001 OBJFE00.0x1cf4 = 0x40000001 +0920c284 OBJFE00.0x1cf8 = 0x920c284 +1c000000 OBJFE00.0x1cfc = 0x1c000000 +20008003 OBJFE00.0x1d00 = 0x20008003 +20064001 OBJFE00.0x1d04 = 0x20064001 +00000003 OBJFE00.0x1d08 = 0x3 +20064001 OBJFE00.0x1d0c = 0x20064001 +7c210023 OBJFE00.0x1d10 = 0x7c210023 +7000c004 OBJFE00.0x1d14 = 0x7000c004 +a0218003 OBJFE00.0x1d18 = 0xa0218003 +48014000 OBJFE00.0x1d1c = 0x48014000 +7c00c023 OBJFE00.0x1d20 = 0x7c00c023 +7000c004 OBJFE00.0x1d24 = 0x7000c004 +b041c043 OBJFE00.0x1d28 = 0xb041c043 +48004000 OBJFE00.0x1d2c = 0x48004000 +80010003 OBJFE00.0x1d30 = 0x80010003 +48014000 OBJFE00.0x1d34 = 0x48014000 +00608005 OBJFE00.0x1d38 = 0x608005 +84000000 OBJFE00.0x1d3c = 0x84000000 +90314043 OBJFE00.0x1d40 = 0x90314043 +48004000 OBJFE00.0x1d44 = 0x48004000 +00408005 OBJFE00.0x1d48 = 0x408005 +94000000 OBJFE00.0x1d4c = 0x94000000 +00001de7 OBJFE00.0x1d50 = 0x1de7 +80000000 OBJFE00.0x1d54 = 0x80000000 +200446c0 OBJFE00.0x1d58 = 0x200446c0 +00000000 OBJFE00.0x1d5c = 0 +0800ffd0 OBJFE00.0x1d60 = 0x800ffd0 +00000012 OBJFE00.0x1d64 = 0x12 +00000000 OBJFE00.0x1d68 = 0 +# out of band: 00000088 081044f4 +# out of band: 0000008c 00011200 +200145a6 OBJFE00.0x1d6c = 0x200145a6 +00000001 OBJFE00.0x1d70 = 0x1 +200446c0 OBJFE00.0x1d74 = 0x200446c0 +00000000 OBJFE00.0x1d78 = 0 +0800ffd0 OBJFE00.0x1d7c = 0x800ffd0 +00000013 OBJFE00.0x1d80 = 0x13 +00000000 OBJFE00.0x1d84 = 0 +# out of band: 00000090 08104604 +# out of band: 00000094 00001e00 +200348e0 OBJFE00.0x1d88 = 0x200348e0 +00010000 OBJFE00.0x1d8c = 0x10000 +00000001 OBJFE00.0x1d90 = 0x1 +00001700 OBJFE00.0x1d94 = 0x1700 +200148e3 OBJFE00.0x1d98 = 0x200148e3 +00000000 OBJFE00.0x1d9c = 0 +603848e4 OBJFE00.0x1da0 = 0x603848e4 +00005de4 OBJFE00.0x1da4 = 0x5de4 +28004404 OBJFE00.0x1da8 = 0x28004404 +94001c04 OBJFE00.0x1dac = 0x94001c04 +2c000000 OBJFE00.0x1db0 = 0x2c000000 +84009c04 OBJFE00.0x1db4 = 0x84009c04 +2c000000 OBJFE00.0x1db8 = 0x2c000000 +20001c03 OBJFE00.0x1dbc = 0x20001c03 +20044000 OBJFE00.0x1dc0 = 0x20044000 +40001d03 OBJFE00.0x1dc4 = 0x40001d03 +48014001 OBJFE00.0x1dc8 = 0x48014001 +53f09d43 OBJFE00.0x1dcc = 0x53f09d43 +48004001 OBJFE00.0x1dd0 = 0x48004001 +7800dc03 OBJFE00.0x1dd4 = 0x7800dc03 +5800c000 OBJFE00.0x1dd8 = 0x5800c000 +08019c03 OBJFE00.0x1ddc = 0x8019c03 +6000c000 OBJFE00.0x1de0 = 0x6000c000 +d0001de4 OBJFE00.0x1de4 = 0xd0001de4 +28004000 OBJFE00.0x1de8 = 0x28004000 +0c21dc43 OBJFE00.0x1dec = 0xc21dc43 +40000000 OBJFE00.0x1df0 = 0x40000000 +c06fde03 OBJFE00.0x1df4 = 0xc06fde03 +48014000 OBJFE00.0x1df8 = 0x48014000 +1c01dc63 OBJFE00.0x1dfc = 0x1c01dc63 +1a0e0000 OBJFE00.0x1e00 = 0x1a0e0000 +fc61dc23 OBJFE00.0x1e04 = 0xfc61dc23 +1b000000 OBJFE00.0x1e08 = 0x1b000000 +a000a1e7 OBJFE00.0x1e0c = 0xa000a1e7 +40000001 OBJFE00.0x1e10 = 0x40000001 +98008004 OBJFE00.0x1e14 = 0x98008004 +2c000000 OBJFE00.0x1e18 = 0x2c000000 +a00001e4 OBJFE00.0x1e1c = 0xa00001e4 +28004000 OBJFE00.0x1e20 = 0x28004000 +20200003 OBJFE00.0x1e24 = 0x20200003 +20014001 OBJFE00.0x1e28 = 0x20014001 +b3f0c043 OBJFE00.0x1e2c = 0xb3f0c043 +48004000 OBJFE00.0x1e30 = 0x48004000 +00610003 OBJFE00.0x1e34 = 0x610003 +48010000 OBJFE00.0x1e38 = 0x48010000 +0c714043 OBJFE00.0x1e3c = 0xc714043 +48000000 OBJFE00.0x1e40 = 0x48000000 +8000c1e4 OBJFE00.0x1e44 = 0x8000c1e4 +28004000 OBJFE00.0x1e48 = 0x28004000 +00400085 OBJFE00.0x1e4c = 0x400085 +84000000 OBJFE00.0x1e50 = 0x84000000 +00208003 OBJFE00.0x1e54 = 0x208003 +20074001 OBJFE00.0x1e58 = 0x20074001 +93f0c043 OBJFE00.0x1e5c = 0x93f0c043 +48004000 OBJFE00.0x1e60 = 0x48004000 +08608003 OBJFE00.0x1e64 = 0x8608003 +48010000 OBJFE00.0x1e68 = 0x48010000 +0c70c043 OBJFE00.0x1e6c = 0xc70c043 +48000000 OBJFE00.0x1e70 = 0x48000000 +00200085 OBJFE00.0x1e74 = 0x200085 +94000000 OBJFE00.0x1e78 = 0x94000000 +00001de7 OBJFE00.0x1e7c = 0x1de7 +80000000 OBJFE00.0x1e80 = 0x80000000 +200446c0 OBJFE00.0x1e84 = 0x200446c0 +00000000 OBJFE00.0x1e88 = 0 +0800ffd0 OBJFE00.0x1e8c = 0x800ffd0 +00000014 OBJFE00.0x1e90 = 0x14 +00000000 OBJFE00.0x1e94 = 0 +# out of band: 00000098 08104620 +# out of band: 0000009c 00011200 +200145a6 OBJFE00.0x1e98 = 0x200145a6 +00000001 OBJFE00.0x1e9c = 0x1 +200446c0 OBJFE00.0x1ea0 = 0x200446c0 +00000000 OBJFE00.0x1ea4 = 0 +0800ffd0 OBJFE00.0x1ea8 = 0x800ffd0 +00000015 OBJFE00.0x1eac = 0x15 +00000000 OBJFE00.0x1eb0 = 0 +# out of band: 000000a0 08104730 +# out of band: 000000a4 00001e00 +200348e0 OBJFE00.0x1eb4 = 0x200348e0 +00010000 OBJFE00.0x1eb8 = 0x10000 +00000001 OBJFE00.0x1ebc = 0x1 +00001600 OBJFE00.0x1ec0 = 0x1600 +200148e3 OBJFE00.0x1ec4 = 0x200148e3 +00000000 OBJFE00.0x1ec8 = 0 +603648e4 OBJFE00.0x1ecc = 0x603648e4 +00005de4 OBJFE00.0x1ed0 = 0x5de4 +28004404 OBJFE00.0x1ed4 = 0x28004404 +94001c04 OBJFE00.0x1ed8 = 0x94001c04 +2c000000 OBJFE00.0x1edc = 0x2c000000 +84009c04 OBJFE00.0x1ee0 = 0x84009c04 +2c000000 OBJFE00.0x1ee4 = 0x2c000000 +20001c03 OBJFE00.0x1ee8 = 0x20001c03 +20044000 OBJFE00.0x1eec = 0x20044000 +40001d03 OBJFE00.0x1ef0 = 0x40001d03 +48014001 OBJFE00.0x1ef4 = 0x48014001 +53f09d43 OBJFE00.0x1ef8 = 0x53f09d43 +48004001 OBJFE00.0x1efc = 0x48004001 +7800dc03 OBJFE00.0x1f00 = 0x7800dc03 +5800c000 OBJFE00.0x1f04 = 0x5800c000 +08019c03 OBJFE00.0x1f08 = 0x8019c03 +6000c000 OBJFE00.0x1f0c = 0x6000c000 +d0001de4 OBJFE00.0x1f10 = 0xd0001de4 +28004000 OBJFE00.0x1f14 = 0x28004000 +0c21dc43 OBJFE00.0x1f18 = 0xc21dc43 +40000000 OBJFE00.0x1f1c = 0x40000000 +c06fde03 OBJFE00.0x1f20 = 0xc06fde03 +48014000 OBJFE00.0x1f24 = 0x48014000 +1c01dc63 OBJFE00.0x1f28 = 0x1c01dc63 +1a0e0000 OBJFE00.0x1f2c = 0x1a0e0000 +fc61dc23 OBJFE00.0x1f30 = 0xfc61dc23 +1b000000 OBJFE00.0x1f34 = 0x1b000000 +8000a1e7 OBJFE00.0x1f38 = 0x8000a1e7 +40000001 OBJFE00.0x1f3c = 0x40000001 +98008004 OBJFE00.0x1f40 = 0x98008004 +2c000000 OBJFE00.0x1f44 = 0x2c000000 +000201e4 OBJFE00.0x1f48 = 0x201e4 +28004001 OBJFE00.0x1f4c = 0x28004001 +a0200003 OBJFE00.0x1f50 = 0xa0200003 +20118000 OBJFE00.0x1f54 = 0x20118000 +b3f0c043 OBJFE00.0x1f58 = 0xb3f0c043 +48004000 OBJFE00.0x1f5c = 0x48004000 +00610003 OBJFE00.0x1f60 = 0x610003 +48010000 OBJFE00.0x1f64 = 0x48010000 +0c714043 OBJFE00.0x1f68 = 0xc714043 +48000000 OBJFE00.0x1f6c = 0x48000000 +80208003 OBJFE00.0x1f70 = 0x80208003 +20118000 OBJFE00.0x1f74 = 0x20118000 +00400085 OBJFE00.0x1f78 = 0x400085 +84000000 OBJFE00.0x1f7c = 0x84000000 +93f0c043 OBJFE00.0x1f80 = 0x93f0c043 +48004000 OBJFE00.0x1f84 = 0x48004000 +08608003 OBJFE00.0x1f88 = 0x8608003 +48010000 OBJFE00.0x1f8c = 0x48010000 +0c70c043 OBJFE00.0x1f90 = 0xc70c043 +48000000 OBJFE00.0x1f94 = 0x48000000 +00200085 OBJFE00.0x1f98 = 0x200085 +94000000 OBJFE00.0x1f9c = 0x94000000 +00001de7 OBJFE00.0x1fa0 = 0x1de7 +80000000 OBJFE00.0x1fa4 = 0x80000000 +200446c0 OBJFE00.0x1fa8 = 0x200446c0 +00000000 OBJFE00.0x1fac = 0 +0800ffd0 OBJFE00.0x1fb0 = 0x800ffd0 +00000016 OBJFE00.0x1fb4 = 0x16 +00000000 OBJFE00.0x1fb8 = 0 +# out of band: 000000a8 0810474c +# out of band: 000000ac 00010a00 +200145a6 OBJFE00.0x1fbc = 0x200145a6 +00000001 OBJFE00.0x1fc0 = 0x1 +200446c0 OBJFE00.0x1fc4 = 0x200446c0 +00000000 OBJFE00.0x1fc8 = 0 +0800ffd0 OBJFE00.0x1fcc = 0x800ffd0 +00000017 OBJFE00.0x1fd0 = 0x17 +00000000 OBJFE00.0x1fd4 = 0 +# out of band: 000000b0 08104854 +# out of band: 000000b4 00001e00 +200348e0 OBJFE00.0x1fd8 = 0x200348e0 +00010000 OBJFE00.0x1fdc = 0x10000 +00000001 OBJFE00.0x1fe0 = 0x1 +00001400 OBJFE00.0x1fe4 = 0x1400 +200148e3 OBJFE00.0x1fe8 = 0x200148e3 +00000000 OBJFE00.0x1fec = 0 +607648e4 OBJFE00.0x1ff0 = 0x607648e4 +00005de4 OBJFE00.0x1ff4 = 0x5de4 +28004404 OBJFE00.0x1ff8 = 0x28004404 +98001c04 OBJFE00.0x1ffc = 0x98001c04 +2c000000 OBJFE00.0x2000 = 0x2c000000 +f0009de4 OBJFE00.0x2004 = 0xf0009de4 +28004000 OBJFE00.0x2008 = 0x28004000 +fc019de4 OBJFE00.0x200c = 0xfc019de4 +28000000 OBJFE00.0x2010 = 0x28000000 +e00fde03 OBJFE00.0x2014 = 0xe00fde03 +48014000 OBJFE00.0x2018 = 0x48014000 +fc21dc43 OBJFE00.0x201c = 0xfc21dc43 +198e0000 OBJFE00.0x2020 = 0x198e0000 +2000dc03 OBJFE00.0x2024 = 0x2000dc03 +50014001 OBJFE00.0x2028 = 0x50014001 +20009c43 OBJFE00.0x202c = 0x20009c43 +20ff4001 OBJFE00.0x2030 = 0x20ff4001 +30009c03 OBJFE00.0x2034 = 0x30009c03 +20844001 OBJFE00.0x2038 = 0x20844001 +00015c03 OBJFE00.0x203c = 0x15c03 +50014001 size 4097, subchannel 2 (0x90c0), offset 0x0004, increment +00011c43 NVC0_COMPUTE.0x4 = 0x11c43 +20ff4001 NVC0_COMPUTE.0x8 = 0x20ff4001 +10011c03 NVC0_COMPUTE.0xc = 0x10011c03 +20884001 NVC0_COMPUTE.SUBCHAN.SEMAPHORE_ADDRESS_HIGH = 0x20884001 +a031dc03 NVC0_COMPUTE.SUBCHAN.SEMAPHORE_ADDRESS_LOW = 0xa031dc03 +48014000 NVC0_COMPUTE.SUBCHAN.SEMAPHORE_SEQUENCE = 0x48014000 +b0221c43 NVC0_COMPUTE.SUBCHAN.SEMAPHORE_TRIGGER = 0xb0221c43 +48004000 NVC0_COMPUTE.SUBCHAN.NOTIFY_INTR = 0x48004000 +80525c03 NVC0_COMPUTE.SUBCHAN.WRCACHE_FLUSH = 0x80525c03 +48014000 NVC0_COMPUTE.0x28 = 0x48014000 +90429c43 NVC0_COMPUTE.0x2c = 0x90429c43 +48004000 NVC0_COMPUTE.0x30 = 0x48004000 +000001e7 NVC0_COMPUTE.0x34 = 0x1e7 +80000000 NVC0_COMPUTE.0x38 = 0x80000000 +94009c04 NVC0_COMPUTE.0x3c = 0x94009c04 +2c000000 NVC0_COMPUTE.0x40 = 0x2c000000 +8400dc04 NVC0_COMPUTE.0x44 = 0x8400dc04 +2c000000 NVC0_COMPUTE.0x48 = 0x2c000000 +d0039de4 NVC0_COMPUTE.0x4c = 0xd0039de4 +28004000 NVC0_COMPUTE.SUBCHAN.REF_CNT = 0x28004000 +20209c03 NVC0_COMPUTE.0x54 = 0x20209c03 +20064000 NVC0_COMPUTE.0x58 = 0x20064000 +4020dd03 NVC0_COMPUTE.0x5c = 0x4020dd03 +48014001 NVC0_COMPUTE.SUBCHAN.DMA_SEMAPHORE = 0x48014001 +60009de4 NVC0_COMPUTE.SUBCHAN.SEMAPHORE_OFFSET = 0x60009de4 +28004000 NVC0_COMPUTE.SUBCHAN.SEMAPHORE_ACQUIRE = 0x28004000 +53f11d43 NVC0_COMPUTE.SUBCHAN.SEMAPHORE_RELEASE = 0x53f11d43 +48004001 NVC0_COMPUTE.0x70 = 0x48004001 +20235c03 NVC0_COMPUTE.0x74 = 0x20235c03 +50014001 NVC0_COMPUTE.0x78 = 0x50014001 +78315c03 NVC0_COMPUTE.0x7c = 0x78315c03 +5800c000 NVC0_COMPUTE.SUBCHAN.YIELD = 0x5800c000 +0832dc03 NVC0_COMPUTE.0x84 = 0x832dc03 +6000c000 NVC0_COMPUTE.0x88 = 0x6000c000 +20231c43 NVC0_COMPUTE.0x8c = 0x20231c43 +20ff4001 NVC0_COMPUTE.0x90 = 0x20ff4001 +23f0dc03 NVC0_COMPUTE.0x94 = 0x23f0dc03 +20984001 NVC0_COMPUTE.0x98 = 0x20984001 +14431c43 NVC0_COMPUTE.0x9c = 0x14431c43 +40000000 NVC0_COMPUTE.0xa0 = 0x40000000 +c0bfde03 NVC0_COMPUTE.0xa4 = 0xc0bfde03 +48014000 NVC0_COMPUTE.0xa8 = 0x48014000 +2d211e84 NVC0_COMPUTE.0xac = 0x2d211e84 +1c000000 NVC0_COMPUTE.0xb0 = 0x1c000000 +3023dc03 NVC0_COMPUTE.0xb4 = 0x3023dc03 +20064001 NVC0_COMPUTE.0xb8 = 0x20064001 +30e1dc63 NVC0_COMPUTE.0xbc = 0x30e1dc63 +1a0e0000 NVC0_COMPUTE.0xc0 = 0x1a0e0000 +00239c03 NVC0_COMPUTE.0xc4 = 0x239c03 +50014001 NVC0_COMPUTE.0xc8 = 0x50014001 +00215c43 NVC0_COMPUTE.0xcc = 0x215c43 +20ff4001 NVC0_COMPUTE.0xd0 = 0x20ff4001 +03f41c03 NVC0_COMPUTE.0xd4 = 0x3f41c03 +208a4001 NVC0_COMPUTE.0xd8 = 0x208a4001 +07f15c23 NVC0_COMPUTE.0xdc = 0x7f15c23 +3088c000 NVC0_COMPUTE.0xe0 = 0x3088c000 +07f11c04 NVC0_COMPUTE.0xe4 = 0x7f11c04 +2010c000 NVC0_COMPUTE.0xe8 = 0x2010c000 +10241c03 NVC0_COMPUTE.0xec = 0x10241c03 +20204001 NVC0_COMPUTE.0xf0 = 0x20204001 +14445c03 NVC0_COMPUTE.0xf4 = 0x14445c03 +68000000 NVC0_COMPUTE.0xf8 = 0x68000000 +fd11dc23 NVC0_COMPUTE.0xfc = 0xfd11dc23 +190e0000 NVC0_COMPUTE.GRAPH.NOP = 0x190e0000 +c00081e7 NVC0_COMPUTE.GRAPH.NOTIFY_ADDRESS_HIGH = 0xc00081e7 +40000000 NVC0_COMPUTE.GRAPH.NOTIFY_ADDRESS_LOW = 0x40000000 +2c712003 NVC0_COMPUTE.GRAPH.NOTIFY = 0x2c712003 +48010000 NVC0_COMPUTE.GRAPH.SERIALIZE = 0x48010000 +30816043 NVC0_COMPUTE.GRAPH.MACRO_UPLOAD_POS = 0x30816043 +48000000 NVC0_COMPUTE.GRAPH.MACRO_UPLOAD_DATA = 0x48000000 +2c90a003 NVC0_COMPUTE.GRAPH.MACRO_ID = 0x2c90a003 +48010000 NVC0_COMPUTE.GRAPH.MACRO_POS = 0x48010000 +00412085 NVC0_COMPUTE.GRAPH.UNK0124 = 0x412085 +84000000 NVC0_COMPUTE.0x128 = 0x84000000 +30a0e043 NVC0_COMPUTE.0x12c = 0x30a0e043 +48000000 NVC0_COMPUTE.GRAPH.COND_ADDRESS_HIGH = 0x48000000 +00212085 NVC0_COMPUTE.GRAPH.COND_ADDRESS_LOW = 0x212085 +94000000 NVC0_COMPUTE.GRAPH.COND_MODE = 0x94000000 +1cd1dc03 NVC0_COMPUTE.GRAPH.UNK013C = 0x1cd1dc03 +48010000 NVC0_COMPUTE.GRAPH.PM_TRIGGER = 0x48010000 +20f21c43 NVC0_COMPUTE.0x144 = 0x20f21c43 +48000000 NVC0_COMPUTE.0x148 = 0x48000000 +60001c03 NVC0_COMPUTE.0x14c = 0x60001c03 +48014000 NVC0_COMPUTE.GRAPH.UNK0150 = 0x48014000 +fc619c43 NVC0_COMPUTE.GRAPH.UNK0154 = 0xfc619c43 +48000000 NVC0_COMPUTE.0x158 = 0x48000000 +e00fdd03 NVC0_COMPUTE.0x15c = 0xe00fdd03 +48014000 NVC0_COMPUTE.0x160 = 0x48014000 +f061dc43 NVC0_COMPUTE.0x164 = 0xf061dc43 +188e4000 NVC0_COMPUTE.0x168 = 0x188e4000 +24e25c03 NVC0_COMPUTE.0x16c = 0x24e25c03 +48010000 NVC0_COMPUTE.0x170 = 0x48010000 +29029c43 NVC0_COMPUTE.0x174 = 0x29029c43 +48000000 NVC0_COMPUTE.0x178 = 0x48000000 +e00001e7 NVC0_COMPUTE.0x17c = 0xe00001e7 +4003fffd NVC0_COMPUTE.0x180 = 0x4003fffd +00001de7 NVC0_COMPUTE.0x184 = 0x1de7 +80000000 NVC0_COMPUTE.0x188 = 0x80000000 +200446c0 NVC0_COMPUTE.0x18c = 0x200446c0 +00000000 NVC0_COMPUTE.0x190 = 0 +0800ffd0 NVC0_COMPUTE.0x194 = 0x800ffd0 +00000018 NVC0_COMPUTE.0x198 = 0x18 +00000000 NVC0_COMPUTE.0x19c = 0 +# out of band: 000000b8 08104870 +# out of band: 000000bc 00020a00 +200145a6 NVC0_COMPUTE.0x1a0 = 0x200145a6 +00000001 NVC0_COMPUTE.0x1a4 = 0x1 +200446c0 NVC0_COMPUTE.0x1a8 = 0x200446c0 +00000000 NVC0_COMPUTE.0x1ac = 0 +0800ffd0 NVC0_COMPUTE.0x1b0 = 0x800ffd0 +00000019 NVC0_COMPUTE.0x1b4 = 0x19 +00000000 NVC0_COMPUTE.0x1b8 = 0 +# out of band: 000000c0 08104a78 +# out of band: 000000c4 00001e00 +200348e0 NVC0_COMPUTE.0x1bc = 0x200348e0 +00010000 NVC0_COMPUTE.0x1c0 = 0x10000 +00000001 NVC0_COMPUTE.0x1c4 = 0x1 +00001300 NVC0_COMPUTE.0x1c8 = 0x1300 +200148e3 NVC0_COMPUTE.0x1cc = 0x200148e3 +00000000 NVC0_COMPUTE.0x1d0 = 0 +602448e4 NVC0_COMPUTE.0x1d4 = 0x602448e4 +00005de4 NVC0_COMPUTE.0x1d8 = 0x5de4 +28004404 NVC0_COMPUTE.0x1dc = 0x28004404 +98009c04 NVC0_COMPUTE.0x1e0 = 0x98009c04 +2c000000 NVC0_COMPUTE.0x1e4 = 0x2c000000 +88011c04 NVC0_COMPUTE.0x1e8 = 0x88011c04 +2c000000 NVC0_COMPUTE.0x1ec = 0x2c000000 +94001c04 NVC0_COMPUTE.0x1f0 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x1f4 = 0x2c000000 +8400dc04 NVC0_COMPUTE.0x1f8 = 0x8400dc04 +2c000000 NVC0_COMPUTE.0x1fc = 0x2c000000 +30211c03 NVC0_COMPUTE.0x200 = 0x30211c03 +20084000 NVC0_COMPUTE.LOCAL_POS_ALLOC = 0x20084000 +20001c03 NVC0_COMPUTE.LOCAL_NEG_ALLOC = 0x20001c03 +20064000 NVC0_COMPUTE.WARP_CSTACK_SIZE = 0x20064000 +9041dc03 NVC0_COMPUTE.TEX_LIMITS = { SAMPLERS_LOG2 = 3 | TEXTURES_LOG2 = 0 | 0x9041dc00 } +188e4000 NVC0_COMPUTE.SHARED_BASE = 0x188e4000 +8001dc03 NVC0_COMPUTE.0x218 = 0x8001dc03 +18804000 NVC0_COMPUTE.MEM_BARRIER = { 0x18804000 } +e000a1e7 NVC0_COMPUTE.0x220 = 0xe000a1e7 +40000000 NVC0_COMPUTE.0x224 = 0x40000000 +a0008003 NVC0_COMPUTE.BIND_TSC = { ACTIVE | SAMPLER = 0 | TSC = 8 | 0xa0000002 } +48004000 NVC0_COMPUTE.BIND_TIC = { TEXTURE = 0 | TIC = 2359328 } +b040c003 NVC0_COMPUTE.BIND_TSC2 = { ACTIVE | SAMPLER = 0 | TSC = 1036 | 0xb0000002 } +48004000 NVC0_COMPUTE.BIND_TIC2 = { TEXTURE = 0 | TIC = 2359328 } +c0018003 NVC0_COMPUTE.GRIDDIM_YX = { X = 32771 | Y = 49153 } +48004000 NVC0_COMPUTE.GRIDDIM_Z = 1207975936 +d041c003 NVC0_COMPUTE.0x240 = 0xd041c003 +48004000 NVC0_COMPUTE.UNK244_TIC_FLUSH = 0x48004000 +00208005 NVC0_COMPUTE.0x248 = 0x208005 +d4015000 NVC0_COMPUTE.SHARED_SIZE = 3556855808 +08000004 NVC0_COMPUTE.THREADS_ALLOC = 0x8000004 +1c000000 NVC0_COMPUTE.BARRIER_ALLOC = 0x1c000000 +04600005 NVC0_COMPUTE.0x258 = 0x4600005 +dc015000 NVC0_COMPUTE.0x25c = 0xdc015000 +00001de7 NVC0_COMPUTE.0x260 = 0x1de7 +80000000 NVC0_COMPUTE.0x264 = 0x80000000 +200446c0 NVC0_COMPUTE.0x268 = 0x200446c0 +00000000 NVC0_COMPUTE.0x26c = 0 +0800ffd0 NVC0_COMPUTE.0x270 = 0x800ffd0 +0000001a NVC0_COMPUTE.0x274 = 0x1a +00000000 NVC0_COMPUTE.0x278 = 0 +# out of band: 000000c8 08104a94 +# out of band: 000000cc 0000c200 +200145a6 NVC0_COMPUTE.0x27c = 0x200145a6 +00000001 NVC0_COMPUTE.0x280 = 0x1 +200446c0 NVC0_COMPUTE.0x284 = 0x200446c0 +00000000 NVC0_COMPUTE.0x288 = 0 +0800ffd0 NVC0_COMPUTE.UNK028C = 0x800ffd0 +0000001b NVC0_COMPUTE.0x290 = 0x1b +00000000 NVC0_COMPUTE.0x294 = 0 +# out of band: 000000d0 08104b54 +# out of band: 000000d4 00001e00 +200348e0 NVC0_COMPUTE.0x298 = 0x200348e0 +00010000 NVC0_COMPUTE.COMPUTE_BEGIN = { 0x10000 } +00000001 NVC0_COMPUTE.UNK02A0 = 0x1 +00001200 NVC0_COMPUTE.0x2a4 = 0x1200 +200148e3 NVC0_COMPUTE.0x2a8 = 0x200148e3 +00000000 NVC0_COMPUTE.0x2ac = 0 +602648e4 NVC0_COMPUTE.0x2b0 = 0x602648e4 +00005de4 NVC0_COMPUTE.0x2b4 = 0x5de4 +28004404 NVC0_COMPUTE.0x2b8 = 0x28004404 +98009c04 NVC0_COMPUTE.0x2bc = 0x98009c04 +2c000000 NVC0_COMPUTE.CP_GPR_ALLOC = 0x2c000000 +88011c04 NVC0_COMPUTE.UNK02C4 = -0.000000 +2c000000 NVC0_COMPUTE.GLOBAL_BASE = { HIGH = 0 | INDEX = 0 | 0x2c000000 } +94001c04 NVC0_COMPUTE.0x2cc = 0x94001c04 +2c000000 NVC0_COMPUTE.0x2d0 = 0x2c000000 +8400dc04 NVC0_COMPUTE.0x2d4 = 0x8400dc04 +2c000000 NVC0_COMPUTE.0x2d8 = 0x2c000000 +30211c03 NVC0_COMPUTE.0x2dc = 0x30211c03 +20084000 NVC0_COMPUTE.0x2e0 = 0x20084000 +20001c03 NVC0_COMPUTE.0x2e4 = 0x20001c03 +20064000 NVC0_COMPUTE.0x2e8 = 0x20064000 +9041dc03 NVC0_COMPUTE.0x2ec = 0x9041dc03 +188e4000 NVC0_COMPUTE.0x2f0 = 0x188e4000 +04001c03 NVC0_COMPUTE.0x2f4 = 0x4001c03 +6000c000 NVC0_COMPUTE.0x2f8 = 0x6000c000 +8001dc03 NVC0_COMPUTE.0x2fc = 0x8001dc03 +18804000 NVC0_COMPUTE.0x300 = 0x18804000 +e000a1e7 NVC0_COMPUTE.0x304 = 0xe000a1e7 +40000000 NVC0_COMPUTE.CACHE_SPLIT = 0x40000000 +a0008003 NVC0_COMPUTE.UNK030C = 0xa0008003 +48004000 NVC0_COMPUTE.0x310 = 0x48004000 +b040c003 NVC0_COMPUTE.0x314 = 0xb040c003 +48004000 NVC0_COMPUTE.0x318 = 0x48004000 +c0018003 NVC0_COMPUTE.0x31c = 0xc0018003 +48004000 NVC0_COMPUTE.0x320 = 0x48004000 +d041c003 NVC0_COMPUTE.0x324 = 0xd041c003 +48004000 NVC0_COMPUTE.0x328 = 0x48004000 +00208045 NVC0_COMPUTE.0x32c = 0x208045 +d4015000 NVC0_COMPUTE.0x330 = 0xd4015000 +08900004 NVC0_COMPUTE.0x334 = 0x8900004 +1c000000 NVC0_COMPUTE.0x338 = 0x1c000000 +04600045 NVC0_COMPUTE.0x33c = 0x4600045 +dc015000 NVC0_COMPUTE.0x340 = 0xdc015000 +00001de7 NVC0_COMPUTE.0x344 = 0x1de7 +80000000 NVC0_COMPUTE.0x348 = 0x80000000 +200446c0 NVC0_COMPUTE.0x34c = 0x200446c0 +00000000 NVC0_COMPUTE.0x350 = 0 +0800ffd0 NVC0_COMPUTE.0x354 = 0x800ffd0 +0000001c NVC0_COMPUTE.0x358 = 0x1c +00000000 NVC0_COMPUTE.0x35c = 0 +# out of band: 000000d8 08104b70 +# out of band: 000000dc 0000ca00 +200145a6 NVC0_COMPUTE.UNK0360 = { UNK1 = 0x1 | 0x200144a6 } +00000001 NVC0_COMPUTE.0x364 = 0x1 +200446c0 NVC0_COMPUTE.LAUNCH = 0x200446c0 +00000000 NVC0_COMPUTE.UNK036C = 0 +0800ffd0 NVC0_COMPUTE.0x370 = 0x800ffd0 +0000001d NVC0_COMPUTE.0x374 = 0x1d +00000000 NVC0_COMPUTE.0x378 = 0 +# out of band: 000000e0 08104c38 +# out of band: 000000e4 00001e00 +200348e0 NVC0_COMPUTE.0x37c = 0x200348e0 +00010000 NVC0_COMPUTE.0x380 = 0x10000 +00000001 NVC0_COMPUTE.0x384 = 0x1 +00001100 NVC0_COMPUTE.0x388 = 0x1100 +200148e3 NVC0_COMPUTE.0x38c = 0x200148e3 +00000000 NVC0_COMPUTE.0x390 = 0 +602448e4 NVC0_COMPUTE.0x394 = 0x602448e4 +00005de4 NVC0_COMPUTE.0x398 = 0x5de4 +28004404 NVC0_COMPUTE.0x39c = 0x28004404 +98009c04 NVC0_COMPUTE.0x3a0 = 0x98009c04 +2c000000 NVC0_COMPUTE.0x3a4 = 0x2c000000 +88011c04 NVC0_COMPUTE.0x3a8 = 0x88011c04 +2c000000 NVC0_COMPUTE.BLOCKDIM_YX = { X = 0 | Y = 11264 } +94001c04 NVC0_COMPUTE.BLOCKDIM_Z = 2483035140 +2c000000 NVC0_COMPUTE.CP_START_ID = 0x2c000000 +8400dc04 NVC0_COMPUTE.0x3b8 = 0x8400dc04 +2c000000 NVC0_COMPUTE.0x3bc = 0x2c000000 +30211c03 NVC0_COMPUTE.0x3c0 = 0x30211c03 +20084000 NVC0_COMPUTE.0x3c4 = 0x20084000 +20001c03 NVC0_COMPUTE.0x3c8 = 0x20001c03 +20064000 NVC0_COMPUTE.0x3cc = 0x20064000 +9041dc03 NVC0_COMPUTE.0x3d0 = 0x9041dc03 +188e4000 NVC0_COMPUTE.0x3d4 = 0x188e4000 +08001c03 NVC0_COMPUTE.0x3d8 = 0x8001c03 +6000c000 NVC0_COMPUTE.0x3dc = 0x6000c000 +8001dc03 NVC0_COMPUTE.0x3e0 = 0x8001dc03 +18804000 NVC0_COMPUTE.0x3e4 = 0x18804000 +c000a1e7 NVC0_COMPUTE.0x3e8 = 0xc000a1e7 +40000000 NVC0_COMPUTE.0x3ec = 0x40000000 +a0008003 NVC0_COMPUTE.0x3f0 = 0xa0008003 +48004000 NVC0_COMPUTE.0x3f4 = 0x48004000 +b040c003 NVC0_COMPUTE.0x3f8 = 0xb040c003 +48004000 NVC0_COMPUTE.0x3fc = 0x48004000 +c0018003 NVC0_COMPUTE.0x400 = 0xc0018003 +48004000 NVC0_COMPUTE.0x404 = 0x48004000 +d041c003 NVC0_COMPUTE.0x408 = 0xd041c003 +48004000 NVC0_COMPUTE.0x40c = 0x48004000 +00208085 NVC0_COMPUTE.0x410 = 0x208085 +d4015000 NVC0_COMPUTE.0x414 = 0xd4015000 +04608085 NVC0_COMPUTE.0x418 = 0x4608085 +dc015000 NVC0_COMPUTE.0x41c = 0xdc015000 +00001de7 NVC0_COMPUTE.0x420 = 0x1de7 +80000000 NVC0_COMPUTE.0x424 = 0x80000000 +200446c0 NVC0_COMPUTE.0x428 = 0x200446c0 +00000000 NVC0_COMPUTE.0x42c = 0 +0800ffd0 NVC0_COMPUTE.0x430 = 0x800ffd0 +0000001e NVC0_COMPUTE.0x434 = 0x1e +00000000 NVC0_COMPUTE.0x438 = 0 +# out of band: 000000e8 08104c54 +# out of band: 000000ec 0000c200 +200145a6 NVC0_COMPUTE.0x43c = 0x200145a6 +00000001 NVC0_COMPUTE.0x440 = 0x1 +200446c0 NVC0_COMPUTE.0x444 = 0x200446c0 +00000000 NVC0_COMPUTE.0x448 = 0 +0800ffd0 NVC0_COMPUTE.0x44c = 0x800ffd0 +0000001f NVC0_COMPUTE.0x450 = 0x1f +00000000 NVC0_COMPUTE.0x454 = 0 +# out of band: 000000f0 08104d14 +# out of band: 000000f4 00001e00 +200348e0 NVC0_COMPUTE.0x458 = 0x200348e0 +00010000 NVC0_COMPUTE.0x45c = 0x10000 +00000001 NVC0_COMPUTE.0x460 = 0x1 +00001000 NVC0_COMPUTE.0x464 = 0x1000 +200148e3 NVC0_COMPUTE.0x468 = 0x200148e3 +00000000 NVC0_COMPUTE.0x46c = 0 +602e48e4 NVC0_COMPUTE.0x470 = 0x602e48e4 +00005de4 NVC0_COMPUTE.0x474 = 0x5de4 +28004404 NVC0_COMPUTE.0x478 = 0x28004404 +98009c04 NVC0_COMPUTE.0x47c = 0x98009c04 +2c000000 NVC0_COMPUTE.0x480 = 0x2c000000 +88011c04 NVC0_COMPUTE.0x484 = 0x88011c04 +2c000000 NVC0_COMPUTE.0x488 = 0x2c000000 +94001c04 NVC0_COMPUTE.0x48c = 0x94001c04 +2c000000 NVC0_COMPUTE.0x490 = 0x2c000000 +8400dc04 NVC0_COMPUTE.0x494 = 0x8400dc04 +2c000000 NVC0_COMPUTE.0x498 = 0x2c000000 +30211c03 NVC0_COMPUTE.0x49c = 0x30211c03 +20084000 NVC0_COMPUTE.0x4a0 = 0x20084000 +20001c03 NVC0_COMPUTE.0x4a4 = 0x20001c03 +20064000 NVC0_COMPUTE.0x4a8 = 0x20064000 +b041dc03 NVC0_COMPUTE.0x4ac = 0xb041dc03 +188e4000 NVC0_COMPUTE.0x4b0 = 0x188e4000 +a001dc03 NVC0_COMPUTE.0x4b4 = 0xa001dc03 +18804000 NVC0_COMPUTE.0x4b8 = 0x18804000 +000021e7 NVC0_COMPUTE.0x4bc = 0x21e7 +80000000 NVC0_COMPUTE.0x4c0 = 0x80000000 +c0409c03 NVC0_COMPUTE.0x4c4 = 0xc0409c03 +50014000 NVC0_COMPUTE.0x4c8 = 0x50014000 +c040dc43 NVC0_COMPUTE.0x4cc = 0xc040dc43 +20ff4000 NVC0_COMPUTE.0x4d0 = 0x20ff4000 +c3f0dc03 NVC0_COMPUTE.0x4d4 = 0xc3f0dc03 +20864000 NVC0_COMPUTE.0x4d8 = 0x20864000 +08009c03 NVC0_COMPUTE.0x4dc = 0x8009c03 +48010000 NVC0_COMPUTE.0x4e0 = 0x48010000 +d040dc03 NVC0_COMPUTE.0x4e4 = 0xd040dc03 +20064000 NVC0_COMPUTE.0x4e8 = 0x20064000 +0ff0dc43 NVC0_COMPUTE.0x4ec = 0xff0dc43 +48000000 NVC0_COMPUTE.0x4f0 = 0x48000000 +80219c03 NVC0_COMPUTE.0x4f4 = 0x80219c03 +48014000 NVC0_COMPUTE.0x4f8 = 0x48014000 +e0009c03 NVC0_COMPUTE.0x4fc = 0xe0009c03 +48004000 NVC0_COMPUTE.FIRMWARE[0] = 0x48004000 +9031dc43 NVC0_COMPUTE.FIRMWARE[0x1] = 0x9031dc43 +48004000 NVC0_COMPUTE.FIRMWARE[0x2] = 0x48004000 +f040dc03 NVC0_COMPUTE.FIRMWARE[0x3] = 0xf040dc03 +48004000 NVC0_COMPUTE.FIRMWARE[0x4] = 0x48004000 +00615c05 NVC0_COMPUTE.FIRMWARE[0x5] = 0x615c05 +84000000 NVC0_COMPUTE.FIRMWARE[0x6] = 0x84000000 +00215c05 NVC0_COMPUTE.FIRMWARE[0x7] = 0x215c05 +dc015000 NVC0_COMPUTE.FIRMWARE[0x8] = 0xdc015000 +00001de7 NVC0_COMPUTE.FIRMWARE[0x9] = 0x1de7 +80000000 NVC0_COMPUTE.FIRMWARE[0xa] = 0x80000000 +200446c0 NVC0_COMPUTE.FIRMWARE[0xb] = 0x200446c0 +00000000 NVC0_COMPUTE.FIRMWARE[0xc] = 0 +0800ffd0 NVC0_COMPUTE.FIRMWARE[0xd] = 0x800ffd0 +00000020 NVC0_COMPUTE.FIRMWARE[0xe] = 0x20 +00000000 NVC0_COMPUTE.FIRMWARE[0xf] = 0 +# out of band: 000000f8 08104d30 +# out of band: 000000fc 0000ea00 +200145a6 NVC0_COMPUTE.FIRMWARE[0x10] = 0x200145a6 +00000001 NVC0_COMPUTE.FIRMWARE[0x11] = 0x1 +200446c0 NVC0_COMPUTE.FIRMWARE[0x12] = 0x200446c0 +00000000 NVC0_COMPUTE.FIRMWARE[0x13] = 0 +0800ffd0 NVC0_COMPUTE.FIRMWARE[0x14] = 0x800ffd0 +00000021 NVC0_COMPUTE.FIRMWARE[0x15] = 0x21 +00000000 NVC0_COMPUTE.FIRMWARE[0x16] = 0 +# out of band: 00000100 08104e18 +# out of band: 00000104 00001e00 +200348e0 NVC0_COMPUTE.FIRMWARE[0x17] = 0x200348e0 +00010000 NVC0_COMPUTE.FIRMWARE[0x18] = 0x10000 +00000001 NVC0_COMPUTE.FIRMWARE[0x19] = 0x1 +00000f00 NVC0_COMPUTE.FIRMWARE[0x1a] = 0xf00 +200148e3 NVC0_COMPUTE.FIRMWARE[0x1b] = 0x200148e3 +00000000 NVC0_COMPUTE.FIRMWARE[0x1c] = 0 +603e48e4 NVC0_COMPUTE.FIRMWARE[0x1d] = 0x603e48e4 +00005de4 NVC0_COMPUTE.FIRMWARE[0x1e] = 0x5de4 +28004404 NVC0_COMPUTE.FIRMWARE[0x1f] = 0x28004404 +98001c04 NVC0_COMPUTE.0x580 = 0x98001c04 +2c000000 NVC0_COMPUTE.0x584 = 0x2c000000 +88011c04 NVC0_COMPUTE.0x588 = 0x88011c04 +2c000000 NVC0_COMPUTE.0x58c = 0x2c000000 +94009c04 NVC0_COMPUTE.0x590 = 0x94009c04 +2c000000 NVC0_COMPUTE.0x594 = 0x2c000000 +8400dc04 NVC0_COMPUTE.0x598 = 0x8400dc04 +2c000000 NVC0_COMPUTE.0x59c = 0x2c000000 +30001c03 NVC0_COMPUTE.0x5a0 = 0x30001c03 +20084000 NVC0_COMPUTE.0x5a4 = 0x20084000 +20209c03 NVC0_COMPUTE.0x5a8 = 0x20209c03 +20064000 NVC0_COMPUTE.0x5ac = 0x20064000 +b001dc03 NVC0_COMPUTE.0x5b0 = 0xb001dc03 +188e4000 NVC0_COMPUTE.0x5b4 = 0x188e4000 +0420dc03 NVC0_COMPUTE.0x5b8 = 0x420dc03 +6000c000 NVC0_COMPUTE.0x5bc = 0x6000c000 +a031dc03 NVC0_COMPUTE.0x5c0 = 0xa031dc03 +18804000 NVC0_COMPUTE.0x5c4 = 0x18804000 +000021e7 NVC0_COMPUTE.0x5c8 = 0x21e7 +80000000 NVC0_COMPUTE.0x5cc = 0x80000000 +c0011de4 NVC0_COMPUTE.0x5d0 = 0xc0011de4 +28004000 NVC0_COMPUTE.0x5d4 = 0x28004000 +d0015de4 NVC0_COMPUTE.0x5d8 = 0xd0015de4 +28004000 NVC0_COMPUTE.0x5dc = 0x28004000 +04411c03 NVC0_COMPUTE.0x5e0 = 0x4411c03 +5800c000 NVC0_COMPUTE.0x5e4 = 0x5800c000 +10511fe3 NVC0_COMPUTE.0x5e8 = 0x10511fe3 +40000000 NVC0_COMPUTE.0x5ec = 0x40000000 +04515c03 NVC0_COMPUTE.0x5f0 = 0x4515c03 +5800c000 NVC0_COMPUTE.0x5f4 = 0x5800c000 +1001dc03 NVC0_COMPUTE.0x5f8 = 0x1001dc03 +50010000 NVC0_COMPUTE.0x5fc = 0x50010000 +10019c43 NVC0_COMPUTE.0x600 = 0x10019c43 +20ff0000 NVC0_COMPUTE.0x604 = 0x20ff0000 +13f19c03 NVC0_COMPUTE.0x608 = 0x13f19c03 +208c0000 NVC0_COMPUTE.0x60c = 0x208c0000 +1c209c03 NVC0_COMPUTE.0x610 = 0x1c209c03 +48010000 NVC0_COMPUTE.0x614 = 0x48010000 +14011c03 NVC0_COMPUTE.0x618 = 0x14011c03 +200c0000 NVC0_COMPUTE.0x61c = 0x200c0000 +13f11c43 NVC0_COMPUTE.0x620 = 0x13f11c43 +48000000 NVC0_COMPUTE.0x624 = 0x48000000 +08209c03 NVC0_COMPUTE.0x628 = 0x8209c03 +48010000 NVC0_COMPUTE.0x62c = 0x48010000 +10411c43 NVC0_COMPUTE.0x630 = 0x10411c43 +48000000 NVC0_COMPUTE.0x634 = 0x48000000 +80219c03 NVC0_COMPUTE.0x638 = 0x80219c03 +48014000 NVC0_COMPUTE.0x63c = 0x48014000 +e0309c03 NVC0_COMPUTE.0x640 = 0xe0309c03 +48004000 NVC0_COMPUTE.0x644 = 0x48004000 +f000dc03 NVC0_COMPUTE.0x648 = 0xf000dc03 +48004000 NVC0_COMPUTE.0x64c = 0x48004000 +9041dc43 NVC0_COMPUTE.0x650 = 0x9041dc43 +48004000 NVC0_COMPUTE.0x654 = 0x48004000 +00611c45 NVC0_COMPUTE.0x658 = 0x611c45 +84000000 NVC0_COMPUTE.0x65c = 0x84000000 +00211c45 NVC0_COMPUTE.0x660 = 0x211c45 +dc015000 NVC0_COMPUTE.0x664 = 0xdc015000 +00001de7 NVC0_COMPUTE.0x668 = 0x1de7 +80000000 NVC0_COMPUTE.0x66c = 0x80000000 +200446c0 NVC0_COMPUTE.0x670 = 0x200446c0 +00000000 NVC0_COMPUTE.0x674 = 0 +0800ffd0 NVC0_COMPUTE.0x678 = 0x800ffd0 +00000022 NVC0_COMPUTE.0x67c = 0x22 +00000000 NVC0_COMPUTE.0x680 = 0 +# out of band: 00000108 08104e34 +# out of band: 0000010c 00012a00 +200145a6 NVC0_COMPUTE.0x684 = 0x200145a6 +00000001 NVC0_COMPUTE.0x688 = 0x1 +200446c0 NVC0_COMPUTE.0x68c = 0x200446c0 +00000000 NVC0_COMPUTE.0x690 = 0 +0800ffd0 NVC0_COMPUTE.0x694 = 0x800ffd0 +00000023 NVC0_COMPUTE.0x698 = 0x23 +00000000 NVC0_COMPUTE.0x69c = 0 +# out of band: 00000110 08104f5c +# out of band: 00000114 00001e00 +200348e0 NVC0_COMPUTE.0x6a0 = 0x200348e0 +00010000 NVC0_COMPUTE.0x6a4 = 0x10000 +00000001 NVC0_COMPUTE.0x6a8 = 0x1 +00000e00 NVC0_COMPUTE.0x6ac = 0xe00 +200148e3 NVC0_COMPUTE.0x6b0 = 0x200148e3 +00000000 NVC0_COMPUTE.0x6b4 = 0 +604048e4 NVC0_COMPUTE.0x6b8 = 0x604048e4 +00005de4 NVC0_COMPUTE.0x6bc = 0x5de4 +28004404 NVC0_COMPUTE.0x6c0 = 0x28004404 +98001c04 NVC0_COMPUTE.0x6c4 = 0x98001c04 +2c000000 NVC0_COMPUTE.0x6c8 = 0x2c000000 +88011c04 NVC0_COMPUTE.0x6cc = 0x88011c04 +2c000000 NVC0_COMPUTE.0x6d0 = 0x2c000000 +94009c04 NVC0_COMPUTE.0x6d4 = 0x94009c04 +2c000000 NVC0_COMPUTE.0x6d8 = 0x2c000000 +8400dc04 NVC0_COMPUTE.0x6dc = 0x8400dc04 +2c000000 NVC0_COMPUTE.0x6e0 = 0x2c000000 +30001c03 NVC0_COMPUTE.0x6e4 = 0x30001c03 +20084000 NVC0_COMPUTE.0x6e8 = 0x20084000 +2020dc03 NVC0_COMPUTE.0x6ec = 0x2020dc03 +20064000 NVC0_COMPUTE.0x6f0 = 0x20064000 +b001dc03 NVC0_COMPUTE.0x6f4 = 0xb001dc03 +188e4000 NVC0_COMPUTE.0x6f8 = 0x188e4000 +08309c03 NVC0_COMPUTE.0x6fc = 0x8309c03 +6000c000 NVC0_COMPUTE.0x700 = 0x6000c000 +a021dc03 NVC0_COMPUTE.0x704 = 0xa021dc03 +18804000 NVC0_COMPUTE.0x708 = 0x18804000 +000021e7 NVC0_COMPUTE.0x70c = 0x21e7 +80000000 NVC0_COMPUTE.0x710 = 0x80000000 +c0011de4 NVC0_COMPUTE.0x714 = 0xc0011de4 +28004000 NVC0_COMPUTE.0x718 = 0x28004000 +d0015de4 NVC0_COMPUTE.0x71c = 0xd0015de4 +28004000 NVC0_COMPUTE.0x720 = 0x28004000 +08411c03 NVC0_COMPUTE.0x724 = 0x8411c03 +5800c000 NVC0_COMPUTE.0x728 = 0x5800c000 +10511fc3 NVC0_COMPUTE.0x72c = 0x10511fc3 +40000000 NVC0_COMPUTE.0x730 = 0x40000000 +08515c03 NVC0_COMPUTE.0x734 = 0x8515c03 +5800c000 NVC0_COMPUTE.0x738 = 0x5800c000 +1001dc03 NVC0_COMPUTE.0x73c = 0x1001dc03 +50010000 NVC0_COMPUTE.0x740 = 0x50010000 +10019c43 NVC0_COMPUTE.0x744 = 0x10019c43 +20ff0000 NVC0_COMPUTE.0x748 = 0x20ff0000 +13f19c03 NVC0_COMPUTE.0x74c = 0x13f19c03 +208c0000 NVC0_COMPUTE.0x750 = 0x208c0000 +1c30dc03 NVC0_COMPUTE.0x754 = 0x1c30dc03 +48010000 NVC0_COMPUTE.MP_LIMIT = 0x48010000 +14011c03 NVC0_COMPUTE.0x75c = 0x14011c03 +200c0000 NVC0_COMPUTE.0x760 = 0x200c0000 +80019de4 NVC0_COMPUTE.0x764 = 0x80019de4 +28004000 NVC0_COMPUTE.0x768 = 0x28004000 +78315c03 NVC0_COMPUTE.0x76c = 0x78315c03 +5800c000 NVC0_COMPUTE.0x770 = 0x5800c000 +13f11c43 NVC0_COMPUTE.0x774 = 0x13f11c43 +48000000 NVC0_COMPUTE.0x778 = 0x48000000 +10319c03 NVC0_COMPUTE.LOCAL_BASE = 0x10319c03 +200dc000 NVC0_COMPUTE.GRIDID = 0x200dc000 +1440dc43 NVC0_COMPUTE.0x784 = 0x1440dc43 +40000000 NVC0_COMPUTE.0x788 = 0x40000000 +e0211c03 NVC0_COMPUTE.0x78c = 0xe0211c03 +48004000 NVC0_COMPUTE.TEMP_ADDRESS_HIGH = 0x48004000 +f0015c03 NVC0_COMPUTE.TEMP_ADDRESS_LOW = 0xf0015c03 +48004000 NVC0_COMPUTE.TEMP_SIZE_HIGH = 0x48004000 +9031dc43 NVC0_COMPUTE.TEMP_SIZE_LOW = 0x9031dc43 +48004000 NVC0_COMPUTE.WARP_TEMP_ALLOC = 0x48004000 +0060dc85 NVC0_COMPUTE.0x7a4 = 0x60dc85 +84000000 NVC0_COMPUTE.0x7a8 = 0x84000000 +0040dc85 NVC0_COMPUTE.0x7ac = 0x40dc85 +dc015000 NVC0_COMPUTE.0x7b0 = 0xdc015000 +00001de7 NVC0_COMPUTE.0x7b4 = 0x1de7 +80000000 NVC0_COMPUTE.0x7b8 = 0x80000000 +200446c0 NVC0_COMPUTE.0x7bc = 0x200446c0 +00000000 NVC0_COMPUTE.0x7c0 = 0 +0800ffd0 NVC0_COMPUTE.0x7c4 = 0x800ffd0 +00000024 NVC0_COMPUTE.0x7c8 = 0x24 +00000000 NVC0_COMPUTE.0x7cc = 0 +# out of band: 00000118 08104f78 +# out of band: 0000011c 00013200 +200145a6 NVC0_COMPUTE.0x7d0 = 0x200145a6 +00000001 NVC0_COMPUTE.0x7d4 = 0x1 +200446c0 NVC0_COMPUTE.0x7d8 = 0x200446c0 +00000000 NVC0_COMPUTE.0x7dc = 0 +0800ffd0 NVC0_COMPUTE.0x7e0 = 0x800ffd0 +00000025 NVC0_COMPUTE.0x7e4 = 0x25 +00000000 NVC0_COMPUTE.0x7e8 = 0 +# out of band: 00000120 081050a8 +# out of band: 00000124 00001e00 +200348e0 NVC0_COMPUTE.0x7ec = 0x200348e0 +00010000 NVC0_COMPUTE.0x7f0 = 0x10000 +00000001 NVC0_COMPUTE.0x7f4 = 0x1 +00000d00 NVC0_COMPUTE.0x7f8 = 0xd00 +200148e3 NVC0_COMPUTE.0x7fc = 0x200148e3 +00000000 NVC0_COMPUTE.0x800 = 0 +602e48e4 NVC0_COMPUTE.0x804 = 0x602e48e4 +00005de4 NVC0_COMPUTE.0x808 = 0x5de4 +28004404 NVC0_COMPUTE.0x80c = 0x28004404 +98009c04 NVC0_COMPUTE.0x810 = 0x98009c04 +2c000000 NVC0_COMPUTE.0x814 = 0x2c000000 +88011c04 NVC0_COMPUTE.0x818 = 0x88011c04 +2c000000 NVC0_COMPUTE.0x81c = 0x2c000000 +94001c04 NVC0_COMPUTE.0x820 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x824 = 0x2c000000 +8400dc04 NVC0_COMPUTE.0x828 = 0x8400dc04 +2c000000 NVC0_COMPUTE.0x82c = 0x2c000000 +30209c03 NVC0_COMPUTE.0x830 = 0x30209c03 +20084000 NVC0_COMPUTE.0x834 = 0x20084000 +20001c03 NVC0_COMPUTE.0x838 = 0x20001c03 +20064000 NVC0_COMPUTE.0x83c = 0x20064000 +b021dc03 NVC0_COMPUTE.0x840 = 0xb021dc03 +188e4000 NVC0_COMPUTE.0x844 = 0x188e4000 +a001dc03 NVC0_COMPUTE.0x848 = 0xa001dc03 +18804000 NVC0_COMPUTE.0x84c = 0x18804000 +000021e7 NVC0_COMPUTE.0x850 = 0x21e7 +80000000 NVC0_COMPUTE.0x854 = 0x80000000 +e0011c03 NVC0_COMPUTE.0x858 = 0xe0011c03 +48004000 NVC0_COMPUTE.0x85c = 0x48004000 +f0215c03 NVC0_COMPUTE.0x860 = 0xf0215c03 +48004000 NVC0_COMPUTE.0x864 = 0x48004000 +c021dc03 NVC0_COMPUTE.0x868 = 0xc021dc03 +50014000 NVC0_COMPUTE.0x86c = 0x50014000 +0040dc05 NVC0_COMPUTE.0x870 = 0x40dc05 +d4015000 NVC0_COMPUTE.0x874 = 0xd4015000 +c0219c43 NVC0_COMPUTE.0x878 = 0xc0219c43 +20ff4000 NVC0_COMPUTE.0x87c = 0x20ff4000 +c3f11c03 NVC0_COMPUTE.0x880 = 0xc3f11c03 +208c4000 NVC0_COMPUTE.0x884 = 0x208c4000 +1c001c03 NVC0_COMPUTE.0x888 = 0x1c001c03 +48010000 NVC0_COMPUTE.0x88c = 0x48010000 +d0211c03 NVC0_COMPUTE.0x890 = 0xd0211c03 +20084000 NVC0_COMPUTE.0x894 = 0x20084000 +13f09c43 NVC0_COMPUTE.0x898 = 0x13f09c43 +48000000 NVC0_COMPUTE.0x89c = 0x48000000 +80011c03 NVC0_COMPUTE.0x8a0 = 0x80011c03 +48014000 NVC0_COMPUTE.0x8a4 = 0x48014000 +90215c43 NVC0_COMPUTE.0x8a8 = 0x90215c43 +48004000 NVC0_COMPUTE.0x8ac = 0x48004000 +0040dc05 NVC0_COMPUTE.0x8b0 = 0x40dc05 +94000000 NVC0_COMPUTE.0x8b4 = 0x94000000 +00001de7 NVC0_COMPUTE.0x8b8 = 0x1de7 +80000000 NVC0_COMPUTE.0x8bc = 0x80000000 +200446c0 NVC0_COMPUTE.0x8c0 = 0x200446c0 +00000000 NVC0_COMPUTE.0x8c4 = 0 +0800ffd0 NVC0_COMPUTE.0x8c8 = 0x800ffd0 +00000026 NVC0_COMPUTE.0x8cc = 0x26 +00000000 NVC0_COMPUTE.0x8d0 = 0 +# out of band: 00000128 081050c4 +# out of band: 0000012c 0000ea00 +200145a6 NVC0_COMPUTE.0x8d4 = 0x200145a6 +00000001 NVC0_COMPUTE.0x8d8 = 0x1 +200446c0 NVC0_COMPUTE.0x8dc = 0x200446c0 +00000000 NVC0_COMPUTE.0x8e0 = 0 +0800ffd0 NVC0_COMPUTE.0x8e4 = 0x800ffd0 +00000027 NVC0_COMPUTE.0x8e8 = 0x27 +00000000 NVC0_COMPUTE.0x8ec = 0 +# out of band: 00000130 081051ac +# out of band: 00000134 00001e00 +200348e0 NVC0_COMPUTE.0x8f0 = 0x200348e0 +00010000 NVC0_COMPUTE.0x8f4 = 0x10000 +00000001 NVC0_COMPUTE.0x8f8 = 0x1 +00000c00 NVC0_COMPUTE.0x8fc = 0xc00 +200148e3 NVC0_COMPUTE.0x900 = 0x200148e3 +00000000 NVC0_COMPUTE.0x904 = 0 +603e48e4 NVC0_COMPUTE.0x908 = 0x603e48e4 +00005de4 NVC0_COMPUTE.0x90c = 0x5de4 +28004404 NVC0_COMPUTE.0x910 = 0x28004404 +98009c04 NVC0_COMPUTE.0x914 = 0x98009c04 +2c000000 NVC0_COMPUTE.0x918 = 0x2c000000 +88011c04 NVC0_COMPUTE.0x91c = 0x88011c04 +2c000000 NVC0_COMPUTE.0x920 = 0x2c000000 +94001c04 NVC0_COMPUTE.0x924 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x928 = 0x2c000000 +8400dc04 NVC0_COMPUTE.0x92c = 0x8400dc04 +2c000000 NVC0_COMPUTE.0x930 = 0x2c000000 +30209c03 NVC0_COMPUTE.0x934 = 0x30209c03 +20084000 NVC0_COMPUTE.0x938 = 0x20084000 +20001c03 NVC0_COMPUTE.0x93c = 0x20001c03 +20064000 NVC0_COMPUTE.0x940 = 0x20064000 +b021dc03 NVC0_COMPUTE.0x944 = 0xb021dc03 +188e4000 NVC0_COMPUTE.0x948 = 0x188e4000 +0400dc03 NVC0_COMPUTE.0x94c = 0x400dc03 +6000c000 NVC0_COMPUTE.0x950 = 0x6000c000 +a031dc03 NVC0_COMPUTE.0x954 = 0xa031dc03 +18804000 NVC0_COMPUTE.0x958 = 0x18804000 +000021e7 NVC0_COMPUTE.0x95c = 0x21e7 +80000000 NVC0_COMPUTE.0x960 = 0x80000000 +e0311c03 NVC0_COMPUTE.0x964 = 0xe0311c03 +48004000 NVC0_COMPUTE.0x968 = 0x48004000 +f0215c03 NVC0_COMPUTE.0x96c = 0xf0215c03 +48004000 NVC0_COMPUTE.0x970 = 0x48004000 +c0019de4 NVC0_COMPUTE.0x974 = 0xc0019de4 +28004000 NVC0_COMPUTE.0x978 = 0x28004000 +0040dc45 NVC0_COMPUTE.0x97c = 0x40dc45 +d4015000 NVC0_COMPUTE.0x980 = 0xd4015000 +04619c03 NVC0_COMPUTE.0x984 = 0x4619c03 +5800c000 NVC0_COMPUTE.0x988 = 0x5800c000 +d0015de4 NVC0_COMPUTE.0x98c = 0xd0015de4 +28004000 NVC0_COMPUTE.0x990 = 0x28004000 +18511fe3 NVC0_COMPUTE.0x994 = 0x18511fe3 +40000000 NVC0_COMPUTE.0x998 = 0x40000000 +04515c03 NVC0_COMPUTE.0x99c = 0x4515c03 +5800c000 NVC0_COMPUTE.0x9a0 = 0x5800c000 +1021dc03 NVC0_COMPUTE.0x9a4 = 0x1021dc03 +50010000 NVC0_COMPUTE.0x9a8 = 0x50010000 +10219c43 NVC0_COMPUTE.0x9ac = 0x10219c43 +20ff0000 NVC0_COMPUTE.0x9b0 = 0x20ff0000 +13f19c03 NVC0_COMPUTE.0x9b4 = 0x13f19c03 +208c0000 NVC0_COMPUTE.0x9b8 = 0x208c0000 +1c001c03 NVC0_COMPUTE.0x9bc = 0x1c001c03 +48010000 NVC0_COMPUTE.0x9c0 = 0x48010000 +14209c03 NVC0_COMPUTE.0x9c4 = 0x14209c03 +200c0000 NVC0_COMPUTE.0x9c8 = 0x200c0000 +0bf09c43 NVC0_COMPUTE.0x9cc = 0xbf09c43 +48000000 NVC0_COMPUTE.0x9d0 = 0x48000000 +00001c03 NVC0_COMPUTE.0x9d4 = 0x1c03 +48010000 NVC0_COMPUTE.0x9d8 = 0x48010000 +08209c43 NVC0_COMPUTE.0x9dc = 0x8209c43 +48000000 NVC0_COMPUTE.0x9e0 = 0x48000000 +80011c03 NVC0_COMPUTE.0x9e4 = 0x80011c03 +48014000 NVC0_COMPUTE.0x9e8 = 0x48014000 +90215c43 NVC0_COMPUTE.0x9ec = 0x90215c43 +48004000 NVC0_COMPUTE.0x9f0 = 0x48004000 +0040dc45 NVC0_COMPUTE.0x9f4 = 0x40dc45 +94000000 NVC0_COMPUTE.0x9f8 = 0x94000000 +00001de7 NVC0_COMPUTE.0x9fc = 0x1de7 +80000000 NVC0_COMPUTE.0xa00 = 0x80000000 +200446c0 NVC0_COMPUTE.COMPUTE_END = { 0x200446c0 } +00000000 NVC0_COMPUTE.UNK0A08 = 0 +0800ffd0 NVC0_COMPUTE.0xa0c = 0x800ffd0 +00000028 NVC0_COMPUTE.0xa10 = 0x28 +00000000 NVC0_COMPUTE.0xa14 = 0 +# out of band: 00000138 081051c8 +# out of band: 0000013c 00012a00 +200145a6 NVC0_COMPUTE.0xa18 = 0x200145a6 +00000001 NVC0_COMPUTE.0xa1c = 0x1 +200446c0 NVC0_COMPUTE.0xa20 = 0x200446c0 +00000000 NVC0_COMPUTE.0xa24 = 0 +0800ffd0 NVC0_COMPUTE.0xa28 = 0x800ffd0 +00000029 NVC0_COMPUTE.0xa2c = 0x29 +00000000 NVC0_COMPUTE.0xa30 = 0 +# out of band: 00000140 081052f0 +# out of band: 00000144 00001e00 +200348e0 NVC0_COMPUTE.0xa34 = 0x200348e0 +00010000 NVC0_COMPUTE.0xa38 = 0x10000 +00000001 NVC0_COMPUTE.0xa3c = 0x1 +00000b00 NVC0_COMPUTE.0xa40 = 0xb00 +200148e3 NVC0_COMPUTE.0xa44 = 0x200148e3 +00000000 NVC0_COMPUTE.0xa48 = 0 +604048e4 NVC0_COMPUTE.0xa4c = 0x604048e4 +00005de4 NVC0_COMPUTE.0xa50 = 0x5de4 +28004404 NVC0_COMPUTE.0xa54 = 0x28004404 +98009c04 NVC0_COMPUTE.0xa58 = 0x98009c04 +2c000000 NVC0_COMPUTE.0xa5c = 0x2c000000 +88011c04 NVC0_COMPUTE.0xa60 = 0x88011c04 +2c000000 NVC0_COMPUTE.0xa64 = 0x2c000000 +94001c04 NVC0_COMPUTE.0xa68 = 0x94001c04 +2c000000 NVC0_COMPUTE.0xa6c = 0x2c000000 +8400dc04 NVC0_COMPUTE.0xa70 = 0x8400dc04 +2c000000 NVC0_COMPUTE.0xa74 = 0x2c000000 +30209c03 NVC0_COMPUTE.0xa78 = 0x30209c03 +20084000 NVC0_COMPUTE.0xa7c = 0x20084000 +20001c03 NVC0_COMPUTE.0xa80 = 0x20001c03 +20064000 NVC0_COMPUTE.0xa84 = 0x20064000 +b021dc03 NVC0_COMPUTE.0xa88 = 0xb021dc03 +188e4000 NVC0_COMPUTE.0xa8c = 0x188e4000 +0800dc03 NVC0_COMPUTE.0xa90 = 0x800dc03 +6000c000 NVC0_COMPUTE.0xa94 = 0x6000c000 +a031dc03 NVC0_COMPUTE.0xa98 = 0xa031dc03 +18804000 NVC0_COMPUTE.0xa9c = 0x18804000 +000021e7 NVC0_COMPUTE.0xaa0 = 0x21e7 +80000000 NVC0_COMPUTE.0xaa4 = 0x80000000 +e0311c03 NVC0_COMPUTE.0xaa8 = 0xe0311c03 +48004000 NVC0_COMPUTE.0xaac = 0x48004000 +f0215c03 NVC0_COMPUTE.0xab0 = 0xf0215c03 +48004000 NVC0_COMPUTE.0xab4 = 0x48004000 +c0019de4 NVC0_COMPUTE.0xab8 = 0xc0019de4 +28004000 NVC0_COMPUTE.0xabc = 0x28004000 +0040dc85 NVC0_COMPUTE.0xac0 = 0x40dc85 +d4015000 NVC0_COMPUTE.0xac4 = 0xd4015000 +08619c03 NVC0_COMPUTE.0xac8 = 0x8619c03 +5800c000 NVC0_COMPUTE.0xacc = 0x5800c000 +d0015de4 NVC0_COMPUTE.0xad0 = 0xd0015de4 +28004000 NVC0_COMPUTE.0xad4 = 0x28004000 +18511fc3 NVC0_COMPUTE.0xad8 = 0x18511fc3 +40000000 NVC0_COMPUTE.0xadc = 0x40000000 +08515c03 NVC0_COMPUTE.0xae0 = 0x8515c03 +5800c000 NVC0_COMPUTE.0xae4 = 0x5800c000 +1021dc03 NVC0_COMPUTE.0xae8 = 0x1021dc03 +50010000 NVC0_COMPUTE.0xaec = 0x50010000 +10219c43 NVC0_COMPUTE.0xaf0 = 0x10219c43 +20ff0000 NVC0_COMPUTE.0xaf4 = 0x20ff0000 +13f19c03 NVC0_COMPUTE.0xaf8 = 0x13f19c03 +208c0000 NVC0_COMPUTE.0xafc = 0x208c0000 +1c001c03 NVC0_COMPUTE.0xb00 = 0x1c001c03 +48010000 NVC0_COMPUTE.0xb04 = 0x48010000 +80011de4 NVC0_COMPUTE.0xb08 = 0x80011de4 +28004000 NVC0_COMPUTE.0xb0c = 0x28004000 +14209c03 NVC0_COMPUTE.0xb10 = 0x14209c03 +200c0000 NVC0_COMPUTE.0xb14 = 0x200c0000 +78015c03 NVC0_COMPUTE.0xb18 = 0x78015c03 +5800c000 NVC0_COMPUTE.0xb1c = 0x5800c000 +0bf09c43 NVC0_COMPUTE.0xb20 = 0xbf09c43 +48000000 NVC0_COMPUTE.0xb24 = 0x48000000 +10011c03 NVC0_COMPUTE.0xb28 = 0x10011c03 +2009c000 NVC0_COMPUTE.0xb2c = 0x2009c000 +14201c43 NVC0_COMPUTE.0xb30 = 0x14201c43 +40000000 NVC0_COMPUTE.0xb34 = 0x40000000 +90015c43 NVC0_COMPUTE.0xb38 = 0x90015c43 +48004000 NVC0_COMPUTE.0xb3c = 0x48004000 +0040dc85 NVC0_COMPUTE.0xb40 = 0x40dc85 +94000000 NVC0_COMPUTE.0xb44 = 0x94000000 +00001de7 NVC0_COMPUTE.0xb48 = 0x1de7 +80000000 NVC0_COMPUTE.0xb4c = 0x80000000 +200446c0 NVC0_COMPUTE.0xb50 = 0x200446c0 +00000000 NVC0_COMPUTE.0xb54 = 0 +0800ffd0 NVC0_COMPUTE.0xb58 = 0x800ffd0 +0000002a NVC0_COMPUTE.0xb5c = 0x2a +00000000 NVC0_COMPUTE.0xb60 = 0 +# out of band: 00000148 0810530c +# out of band: 0000014c 00013200 +200145a6 NVC0_COMPUTE.0xb64 = 0x200145a6 +00000001 NVC0_COMPUTE.0xb68 = 0x1 +200446c0 NVC0_COMPUTE.0xb6c = 0x200446c0 +00000000 NVC0_COMPUTE.0xb70 = 0 +0800ffd0 NVC0_COMPUTE.0xb74 = 0x800ffd0 +0000002b NVC0_COMPUTE.0xb78 = 0x2b +00000000 NVC0_COMPUTE.0xb7c = 0 +# out of band: 00000150 0810543c +# out of band: 00000154 00001e00 +200348e0 NVC0_COMPUTE.0xb80 = 0x200348e0 +00010000 NVC0_COMPUTE.0xb84 = 0x10000 +00000001 NVC0_COMPUTE.0xb88 = 0x1 +00003200 NVC0_COMPUTE.0xb8c = 0x3200 +200148e3 NVC0_COMPUTE.0xb90 = 0x200148e3 +00000000 NVC0_COMPUTE.0xb94 = 0 +609848e4 NVC0_COMPUTE.0xb98 = 0x609848e4 +00005de4 NVC0_COMPUTE.0xb9c = 0x5de4 +28004404 NVC0_COMPUTE.0xba0 = 0x28004404 +94001c04 NVC0_COMPUTE.0xba4 = 0x94001c04 +2c000000 NVC0_COMPUTE.0xba8 = 0x2c000000 +84009c04 NVC0_COMPUTE.0xbac = 0x84009c04 +2c000000 NVC0_COMPUTE.0xbb0 = 0x2c000000 +08001d03 NVC0_COMPUTE.0xbb4 = 0x8001d03 +40000000 NVC0_COMPUTE.0xbb8 = 0x40000000 +e00fdd03 NVC0_COMPUTE.0xbbc = 0xe00fdd03 +48014000 NVC0_COMPUTE.0xbc0 = 0x48014000 +f3f1dc43 NVC0_COMPUTE.0xbc4 = 0xf3f1dc43 +1b0e4000 NVC0_COMPUTE.0xbc8 = 0x1b0e4000 +200001e7 NVC0_COMPUTE.0xbcc = 0x200001e7 +40000001 NVC0_COMPUTE.0xbd0 = 0x40000001 +10019de2 NVC0_COMPUTE.0xbd4 = 0x10019de2 +18000000 NVC0_COMPUTE.0xbd8 = 0x18000000 +7800dc03 NVC0_COMPUTE.0xbdc = 0x7800dc03 +5800c000 NVC0_COMPUTE.0xbe0 = 0x5800c000 +a0011c03 NVC0_COMPUTE.0xbe4 = 0xa0011c03 +200d8000 NVC0_COMPUTE.0xbe8 = 0x200d8000 +b0315c43 NVC0_COMPUTE.0xbec = 0xb0315c43 +48004000 NVC0_COMPUTE.0xbf0 = 0x48004000 +80019c03 NVC0_COMPUTE.0xbf4 = 0x80019c03 +200d8000 NVC0_COMPUTE.0xbf8 = 0x200d8000 +00409c85 NVC0_COMPUTE.0xbfc = 0x409c85 +84000000 NVC0_COMPUTE.0xc00 = 0x84000000 +9031dc43 NVC0_COMPUTE.0xc04 = 0x9031dc43 +48004000 NVC0_COMPUTE.0xc08 = 0x48004000 +00609c85 NVC0_COMPUTE.0xc0c = 0x609c85 +94000000 NVC0_COMPUTE.0xc10 = 0x94000000 +60001de7 NVC0_COMPUTE.0xc14 = 0x60001de7 +40000007 NVC0_COMPUTE.0xc18 = 0x40000007 +e00fdd03 NVC0_COMPUTE.0xc1c = 0xe00fdd03 +48014000 NVC0_COMPUTE.0xc20 = 0x48014000 +f3f1dc43 NVC0_COMPUTE.0xc24 = 0xf3f1dc43 +1a8e4000 NVC0_COMPUTE.0xc28 = 0x1a8e4000 +000001e7 NVC0_COMPUTE.0xc2c = 0x1e7 +40000003 NVC0_COMPUTE.0xc30 = 0x40000003 +c0009de4 NVC0_COMPUTE.0xc34 = 0xc0009de4 +28004000 NVC0_COMPUTE.0xc38 = 0x28004000 +d0001de4 NVC0_COMPUTE.0xc3c = 0xd0001de4 +28004000 NVC0_COMPUTE.0xc40 = 0x28004000 +042fdd03 NVC0_COMPUTE.0xc44 = 0x42fdd03 +4801c000 NVC0_COMPUTE.0xc48 = 0x4801c000 +fc01dc43 NVC0_COMPUTE.0xc4c = 0xfc01dc43 +188e0000 NVC0_COMPUTE.0xc50 = 0x188e0000 +000001e7 NVC0_COMPUTE.0xc54 = 0x1e7 +80000000 NVC0_COMPUTE.0xc58 = 0x80000000 +fc01dde2 NVC0_COMPUTE.0xc5c = 0xfc01dde2 +1bffffff NVC0_COMPUTE.0xc60 = 0x1bffffff +04009de2 NVC0_COMPUTE.0xc64 = 0x4009de2 +18000000 NVC0_COMPUTE.0xc68 = 0x18000000 +fc00dde4 NVC0_COMPUTE.0xc6c = 0xfc00dde4 +28000000 NVC0_COMPUTE.0xc70 = 0x28000000 +a0711c03 NVC0_COMPUTE.0xc74 = 0xa0711c03 +48014000 NVC0_COMPUTE.0xc78 = 0x48014000 +b0715c43 NVC0_COMPUTE.0xc7c = 0xb0715c43 +48004000 NVC0_COMPUTE.0xc80 = 0x48004000 +80719c03 NVC0_COMPUTE.0xc84 = 0x80719c03 +48014000 NVC0_COMPUTE.0xc88 = 0x48014000 +9071dc43 NVC0_COMPUTE.0xc8c = 0x9071dc43 +48004000 NVC0_COMPUTE.0xc90 = 0x48004000 +00401c05 NVC0_COMPUTE.0xc94 = 0x401c05 +84000000 NVC0_COMPUTE.0xc98 = 0x84000000 +04209c03 NVC0_COMPUTE.0xc9c = 0x4209c03 +4801c000 NVC0_COMPUTE.0xca0 = 0x4801c000 +fc30dc43 NVC0_COMPUTE.0xca4 = 0xfc30dc43 +48000000 NVC0_COMPUTE.0xca8 = 0x48000000 +c02fdd03 NVC0_COMPUTE.0xcac = 0xc02fdd03 +48014000 NVC0_COMPUTE.0xcb0 = 0x48014000 +d031dc43 NVC0_COMPUTE.0xcb4 = 0xd031dc43 +198e4000 NVC0_COMPUTE.0xcb8 = 0x198e4000 +fc411c03 NVC0_COMPUTE.0xcbc = 0xfc411c03 +4801ffff NVC0_COMPUTE.0xcc0 = 0x4801ffff +fc515c43 NVC0_COMPUTE.0xcc4 = 0xfc515c43 +4800ffff NVC0_COMPUTE.0xcc8 = 0x4800ffff +00601c05 NVC0_COMPUTE.0xccc = 0x601c05 +94000000 NVC0_COMPUTE.0xcd0 = 0x94000000 +fc619c03 NVC0_COMPUTE.0xcd4 = 0xfc619c03 +4801ffff NVC0_COMPUTE.0xcd8 = 0x4801ffff +fc71dc43 NVC0_COMPUTE.0xcdc = 0xfc71dc43 +4800ffff NVC0_COMPUTE.0xce0 = 0x4800ffff +a00001e7 NVC0_COMPUTE.0xce4 = 0xa00001e7 +4003fffe NVC0_COMPUTE.0xce8 = 0x4003fffe +00001de7 NVC0_COMPUTE.0xcec = 0x1de7 +40000004 NVC0_COMPUTE.0xcf0 = 0x40000004 +e0009de4 NVC0_COMPUTE.0xcf4 = 0xe0009de4 +28004000 NVC0_COMPUTE.0xcf8 = 0x28004000 +04209c03 NVC0_COMPUTE.0xcfc = 0x4209c03 +4801c000 NVC0_COMPUTE.0xd00 = 0x4801c000 +f3f0dc43 NVC0_COMPUTE.0xd04 = 0xf3f0dc43 +48004000 NVC0_COMPUTE.0xd08 = 0x48004000 +080fdd03 NVC0_COMPUTE.0xd0c = 0x80fdd03 +48010000 NVC0_COMPUTE.0xd10 = 0x48010000 +0ff1dc43 NVC0_COMPUTE.0xd14 = 0xff1dc43 +1a8e0000 NVC0_COMPUTE.0xd18 = 0x1a8e0000 +000001e7 NVC0_COMPUTE.0xd1c = 0x1e7 +80000000 NVC0_COMPUTE.0xd20 = 0x80000000 +03ffde03 NVC0_COMPUTE.0xd24 = 0x3ffde03 +48014001 NVC0_COMPUTE.0xd28 = 0x48014001 +10001de4 NVC0_COMPUTE.0xd2c = 0x10001de4 +28004001 NVC0_COMPUTE.0xd30 = 0x28004001 +fc01dc43 NVC0_COMPUTE.0xd34 = 0xfc01dc43 +190e0000 NVC0_COMPUTE.0xd38 = 0x190e0000 +000001e7 NVC0_COMPUTE.0xd3c = 0x1e7 +80000000 NVC0_COMPUTE.0xd40 = 0x80000000 +e0011de4 NVC0_COMPUTE.0xd44 = 0xe0011de4 +28004000 NVC0_COMPUTE.0xd48 = 0x28004000 +f000dde4 NVC0_COMPUTE.0xd4c = 0xf000dde4 +28004000 NVC0_COMPUTE.0xd50 = 0x28004000 +10015de2 NVC0_COMPUTE.0xd54 = 0x10015de2 +18000000 NVC0_COMPUTE.0xd58 = 0x18000000 +78401c03 NVC0_COMPUTE.0xd5c = 0x78401c03 +5800c000 NVC0_COMPUTE.0xd60 = 0x5800c000 +a0409c03 NVC0_COMPUTE.CALL_LIMIT_LOG = 0xa0409c03 +200b8000 NVC0_COMPUTE.0xd68 = 0x200b8000 +0031dc43 NVC0_COMPUTE.0xd6c = 0x31dc43 +40000000 NVC0_COMPUTE.0xd70 = 0x40000000 +b070dc43 NVC0_COMPUTE.0xd74 = 0xb070dc43 +48004000 NVC0_COMPUTE.0xd78 = 0x48004000 +80419c03 NVC0_COMPUTE.0xd7c = 0x80419c03 +200b8000 NVC0_COMPUTE.0xd80 = 0x200b8000 +fc011de4 NVC0_COMPUTE.0xd84 = 0xfc011de4 +28000000 NVC0_COMPUTE.0xd88 = 0x28000000 +fc015de4 NVC0_COMPUTE.0xd8c = 0xfc015de4 +28000000 NVC0_COMPUTE.0xd90 = 0x28000000 +9071dc43 NVC0_COMPUTE.UNK0D94 = 0x9071dc43 +48004000 NVC0_COMPUTE.0xd98 = 0x48004000 +00201c05 NVC0_COMPUTE.0xd9c = 0x201c05 +84000000 NVC0_COMPUTE.0xda0 = 0x84000000 +04411c03 NVC0_COMPUTE.0xda4 = 0x4411c03 +4801c000 NVC0_COMPUTE.0xda8 = 0x4801c000 +fc515c43 NVC0_COMPUTE.0xdac = 0xfc515c43 +48000000 NVC0_COMPUTE.0xdb0 = 0x48000000 +004fdd03 NVC0_COMPUTE.0xdb4 = 0x4fdd03 +48014001 NVC0_COMPUTE.0xdb8 = 0x48014001 +1051dc43 NVC0_COMPUTE.0xdbc = 0x1051dc43 +188e4001 NVC0_COMPUTE.0xdc0 = 0x188e4001 +04209c03 NVC0_COMPUTE.0xdc4 = 0x4209c03 +4801c000 NVC0_COMPUTE.0xdc8 = 0x4801c000 +fc30dc43 NVC0_COMPUTE.0xdcc = 0xfc30dc43 +48000000 NVC0_COMPUTE.0xdd0 = 0x48000000 +00601c05 NVC0_COMPUTE.0xdd4 = 0x601c05 +94000000 NVC0_COMPUTE.0xdd8 = 0x94000000 +04619c03 NVC0_COMPUTE.0xddc = 0x4619c03 +4801c000 NVC0_COMPUTE.0xde0 = 0x4801c000 +fc71dc43 NVC0_COMPUTE.WATCHDOG_TIMER = 4235320387 +48000000 NVC0_COMPUTE.0xde8 = 0x48000000 +a00001e7 NVC0_COMPUTE.0xdec = 0xa00001e7 +4003fffe NVC0_COMPUTE.0xdf0 = 0x4003fffe +00001de7 NVC0_COMPUTE.0xdf4 = 0x1de7 +80000000 NVC0_COMPUTE.0xdf8 = 0x80000000 +200446c0 NVC0_COMPUTE.0xdfc = 0x200446c0 +00000000 NVC0_COMPUTE.0xe00 = 0 +0800ffd0 NVC0_COMPUTE.0xe04 = 0x800ffd0 +0000002c NVC0_COMPUTE.0xe08 = 0x2c +00000000 NVC0_COMPUTE.0xe0c = 0 +# out of band: 00000158 08105458 +# out of band: 0000015c 00029200 +200145a6 NVC0_COMPUTE.0xe10 = 0x200145a6 +00000001 NVC0_COMPUTE.0xe14 = 0x1 +200446c0 NVC0_COMPUTE.0xe18 = 0x200446c0 +00000000 NVC0_COMPUTE.0xe1c = 0 +0800ffd0 NVC0_COMPUTE.0xe20 = 0x800ffd0 +0000002d NVC0_COMPUTE.0xe24 = 0x2d +00000000 NVC0_COMPUTE.0xe28 = 0 +# out of band: 00000160 081056e8 +# out of band: 00000164 00001e00 +200348e0 NVC0_COMPUTE.0xe2c = 0x200348e0 +00010000 NVC0_COMPUTE.0xe30 = 0x10000 +00000001 NVC0_COMPUTE.0xe34 = 0x1 +00003100 NVC0_COMPUTE.0xe38 = 0x3100 +200148e3 NVC0_COMPUTE.0xe3c = 0x200148e3 +00000000 NVC0_COMPUTE.0xe40 = 0 +602248e4 NVC0_COMPUTE.0xe44 = 0x602248e4 +00005de4 NVC0_COMPUTE.0xe48 = 0x5de4 +28004404 NVC0_COMPUTE.0xe4c = 0x28004404 +94001c04 NVC0_COMPUTE.0xe50 = 0x94001c04 +2c000000 NVC0_COMPUTE.0xe54 = 0x2c000000 +84009c04 NVC0_COMPUTE.0xe58 = 0x84009c04 +2c000000 NVC0_COMPUTE.0xe5c = 0x2c000000 +08001d03 NVC0_COMPUTE.0xe60 = 0x8001d03 +40000000 NVC0_COMPUTE.0xe64 = 0x40000000 +d0009de4 NVC0_COMPUTE.0xe68 = 0xd0009de4 +28004000 NVC0_COMPUTE.0xe6c = 0x28004000 +c00fde03 NVC0_COMPUTE.0xe70 = 0xc00fde03 +48014000 NVC0_COMPUTE.0xe74 = 0x48014000 +fc21dc43 NVC0_COMPUTE.0xe78 = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0xe7c = 0x198e0000 +000081e7 NVC0_COMPUTE.0xe80 = 0x81e7 +40000001 NVC0_COMPUTE.0xe84 = 0x40000001 +1001a1e2 NVC0_COMPUTE.0xe88 = 0x1001a1e2 +18000000 NVC0_COMPUTE.0xe8c = 0x18000000 +7800e003 NVC0_COMPUTE.0xe90 = 0x7800e003 +5800c000 NVC0_COMPUTE.0xe94 = 0x5800c000 +a0012003 NVC0_COMPUTE.0xe98 = 0xa0012003 +200d8000 NVC0_COMPUTE.0xe9c = 0x200d8000 +b0316043 NVC0_COMPUTE.0xea0 = 0xb0316043 +48004000 NVC0_COMPUTE.0xea4 = 0x48004000 +8001a003 NVC0_COMPUTE.0xea8 = 0x8001a003 +200d8000 NVC0_COMPUTE.0xeac = 0x200d8000 +0040a085 NVC0_COMPUTE.0xeb0 = 0x40a085 +84000000 NVC0_COMPUTE.0xeb4 = 0x84000000 +9031e043 NVC0_COMPUTE.0xeb8 = 0x9031e043 +48004000 NVC0_COMPUTE.0xebc = 0x48004000 +0060a085 NVC0_COMPUTE.0xec0 = 0x60a085 +94000000 NVC0_COMPUTE.0xec4 = 0x94000000 +00001de7 NVC0_COMPUTE.0xec8 = 0x1de7 +80000000 NVC0_COMPUTE.0xecc = 0x80000000 +200446c0 NVC0_COMPUTE.0xed0 = 0x200446c0 +00000000 NVC0_COMPUTE.0xed4 = 0 +0800ffd0 NVC0_COMPUTE.0xed8 = 0x800ffd0 +0000002e NVC0_COMPUTE.0xedc = 0x2e +00000000 NVC0_COMPUTE.0xee0 = 0 +# out of band: 00000168 08105704 +# out of band: 0000016c 0000ba00 +200145a6 NVC0_COMPUTE.0xee4 = 0x200145a6 +00000001 NVC0_COMPUTE.0xee8 = 0x1 +200446c0 NVC0_COMPUTE.0xeec = 0x200446c0 +00000000 NVC0_COMPUTE.0xef0 = 0 +0800ffd0 NVC0_COMPUTE.0xef4 = 0x800ffd0 +0000002f NVC0_COMPUTE.0xef8 = 0x2f +00000000 NVC0_COMPUTE.0xefc = 0 +# out of band: 00000170 081057bc +# out of band: 00000174 00001e00 +200348e0 NVC0_COMPUTE.0xf00 = 0x200348e0 +00010000 NVC0_COMPUTE.0xf04 = 0x10000 +00000001 NVC0_COMPUTE.0xf08 = 0x1 +00003000 NVC0_COMPUTE.0xf0c = 0x3000 +200148e3 NVC0_COMPUTE.0xf10 = 0x200148e3 +00000000 NVC0_COMPUTE.0xf14 = 0 +603848e4 NVC0_COMPUTE.0xf18 = 0x603848e4 +00005de4 NVC0_COMPUTE.0xf1c = 0x5de4 +28004404 NVC0_COMPUTE.0xf20 = 0x28004404 +94001c04 NVC0_COMPUTE.0xf24 = 0x94001c04 +2c000000 NVC0_COMPUTE.0xf28 = 0x2c000000 +84009c04 NVC0_COMPUTE.0xf2c = 0x84009c04 +2c000000 NVC0_COMPUTE.0xf30 = 0x2c000000 +08001d03 NVC0_COMPUTE.0xf34 = 0x8001d03 +40000000 NVC0_COMPUTE.0xf38 = 0x40000000 +d0009de4 NVC0_COMPUTE.0xf3c = 0xd0009de4 +28004000 NVC0_COMPUTE.0xf40 = 0x28004000 +c00fde03 NVC0_COMPUTE.0xf44 = 0xc00fde03 +48014000 NVC0_COMPUTE.0xf48 = 0x48014000 +fc21dc43 NVC0_COMPUTE.0xf4c = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0xf50 = 0x198e0000 +e00001e7 NVC0_COMPUTE.0xf54 = 0xe00001e7 +40000000 NVC0_COMPUTE.0xf58 = 0x40000000 +a0009c03 NVC0_COMPUTE.0xf5c = 0xa0009c03 +48014000 NVC0_COMPUTE.0xf60 = 0x48014000 +b3f0dc43 NVC0_COMPUTE.0xf64 = 0xb3f0dc43 +48004000 NVC0_COMPUTE.0xf68 = 0x48004000 +80011c03 NVC0_COMPUTE.0xf6c = 0x80011c03 +48014000 NVC0_COMPUTE.0xf70 = 0x48014000 +00209c05 NVC0_COMPUTE.0xf74 = 0x209c05 +84000000 NVC0_COMPUTE.0xf78 = 0x84000000 +93f15c43 NVC0_COMPUTE.0xf7c = 0x93f15c43 +48004000 NVC0_COMPUTE.0xf80 = 0x48004000 +00409c05 NVC0_COMPUTE.0xf84 = 0x409c05 +94000000 NVC0_COMPUTE.0xf88 = 0x94000000 +80001de7 NVC0_COMPUTE.0xf8c = 0x80001de7 +40000001 NVC0_COMPUTE.0xf90 = 0x40000001 +000fde03 NVC0_COMPUTE.0xf94 = 0xfde03 +48014001 NVC0_COMPUTE.0xf98 = 0x48014001 +10009de4 NVC0_COMPUTE.0xf9c = 0x10009de4 +28004001 NVC0_COMPUTE.0xfa0 = 0x28004001 +fc21dc43 NVC0_COMPUTE.0xfa4 = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0xfa8 = 0x198e0000 +000081e7 NVC0_COMPUTE.0xfac = 0x81e7 +40000001 NVC0_COMPUTE.0xfb0 = 0x40000001 +e000a003 NVC0_COMPUTE.0xfb4 = 0xe000a003 +48014000 NVC0_COMPUTE.0xfb8 = 0x48014000 +f3f0e043 NVC0_COMPUTE.0xfbc = 0xf3f0e043 +48004000 NVC0_COMPUTE.0xfc0 = 0x48004000 +a0212003 NVC0_COMPUTE.0xfc4 = 0xa0212003 +48014000 NVC0_COMPUTE.0xfc8 = 0x48014000 +b0316043 NVC0_COMPUTE.0xfcc = 0xb0316043 +48004000 NVC0_COMPUTE.0xfd0 = 0x48004000 +8020a003 NVC0_COMPUTE.0xfd4 = 0x8020a003 +48014000 NVC0_COMPUTE.0xfd8 = 0x48014000 +00402005 NVC0_COMPUTE.0xfdc = 0x402005 +84000000 NVC0_COMPUTE.0xfe0 = 0x84000000 +9030e043 NVC0_COMPUTE.0xfe4 = 0x9030e043 +48004000 NVC0_COMPUTE.0xfe8 = 0x48004000 +00202005 NVC0_COMPUTE.0xfec = 0x202005 +94000000 NVC0_COMPUTE.0xff0 = 0x94000000 +00001de7 NVC0_COMPUTE.0xff4 = 0x1de7 +80000000 NVC0_COMPUTE.0xff8 = 0x80000000 +200446c0 NVC0_COMPUTE.0xffc = 0x200446c0 +00000000 NVC0_COMPUTE.0x1000 = 0 +0800ffd0 NVC0_COMPUTE.0x1004 = 0x800ffd0 +00000030 NVC0_COMPUTE.0x1008 = 0x30 +00000000 NVC0_COMPUTE.0x100c = 0 +# out of band: 00000178 081057d8 +# out of band: 0000017c 00011200 +200145a6 NVC0_COMPUTE.0x1010 = 0x200145a6 +00000001 NVC0_COMPUTE.0x1014 = 0x1 +200446c0 NVC0_COMPUTE.0x1018 = 0x200446c0 +00000000 NVC0_COMPUTE.0x101c = 0 +0800ffd0 NVC0_COMPUTE.0x1020 = 0x800ffd0 +00000031 NVC0_COMPUTE.0x1024 = 0x31 +00000000 NVC0_COMPUTE.0x1028 = 0 +# out of band: 00000180 081058e8 +# out of band: 00000184 00001e00 +200348e0 NVC0_COMPUTE.0x102c = 0x200348e0 +00010000 NVC0_COMPUTE.0x1030 = 0x10000 +00000001 NVC0_COMPUTE.0x1034 = 0x1 +00002f00 NVC0_COMPUTE.0x1038 = 0x2f00 +200148e3 NVC0_COMPUTE.0x103c = 0x200148e3 +00000000 NVC0_COMPUTE.0x1040 = 0 +601e48e4 NVC0_COMPUTE.0x1044 = 0x601e48e4 +00005de4 NVC0_COMPUTE.0x1048 = 0x5de4 +28004404 NVC0_COMPUTE.0x104c = 0x28004404 +94001c04 NVC0_COMPUTE.0x1050 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x1054 = 0x2c000000 +84009c04 NVC0_COMPUTE.0x1058 = 0x84009c04 +2c000000 NVC0_COMPUTE.0x105c = 0x2c000000 +08001d03 NVC0_COMPUTE.0x1060 = 0x8001d03 +40000000 NVC0_COMPUTE.0x1064 = 0x40000000 +d0009de4 NVC0_COMPUTE.0x1068 = 0xd0009de4 +28004000 NVC0_COMPUTE.0x106c = 0x28004000 +c00fde03 NVC0_COMPUTE.0x1070 = 0xc00fde03 +48014000 NVC0_COMPUTE.0x1074 = 0x48014000 +fc21dc43 NVC0_COMPUTE.0x1078 = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0x107c = 0x198e0000 +c00081e7 NVC0_COMPUTE.0x1080 = 0xc00081e7 +40000000 NVC0_COMPUTE.0x1084 = 0x40000000 +a000a003 NVC0_COMPUTE.0x1088 = 0xa000a003 +48014000 NVC0_COMPUTE.0x108c = 0x48014000 +b3f0e043 NVC0_COMPUTE.0x1090 = 0xb3f0e043 +48004000 NVC0_COMPUTE.0x1094 = 0x48004000 +80012003 NVC0_COMPUTE.0x1098 = 0x80012003 +48014000 NVC0_COMPUTE.0x109c = 0x48014000 +0020a005 NVC0_COMPUTE.0x10a0 = 0x20a005 +84000000 NVC0_COMPUTE.0x10a4 = 0x84000000 +93f16043 NVC0_COMPUTE.0x10a8 = 0x93f16043 +48004000 NVC0_COMPUTE.0x10ac = 0x48004000 +0040a005 NVC0_COMPUTE.0x10b0 = 0x40a005 +94000000 NVC0_COMPUTE.0x10b4 = 0x94000000 +00001de7 NVC0_COMPUTE.0x10b8 = 0x1de7 +80000000 NVC0_COMPUTE.0x10bc = 0x80000000 +200446c0 NVC0_COMPUTE.0x10c0 = 0x200446c0 +00000000 NVC0_COMPUTE.0x10c4 = 0 +0800ffd0 NVC0_COMPUTE.0x10c8 = 0x800ffd0 +00000032 NVC0_COMPUTE.0x10cc = 0x32 +00000000 NVC0_COMPUTE.0x10d0 = 0 +# out of band: 00000188 08105904 +# out of band: 0000018c 0000aa00 +200145a6 NVC0_COMPUTE.0x10d4 = 0x200145a6 +00000001 NVC0_COMPUTE.0x10d8 = 0x1 +200446c0 NVC0_COMPUTE.0x10dc = 0x200446c0 +00000000 NVC0_COMPUTE.0x10e0 = 0 +0800ffd0 NVC0_COMPUTE.0x10e4 = 0x800ffd0 +00000033 NVC0_COMPUTE.0x10e8 = 0x33 +00000000 NVC0_COMPUTE.0x10ec = 0 +# out of band: 00000190 081059ac +# out of band: 00000194 00001e00 +200348e0 NVC0_COMPUTE.0x10f0 = 0x200348e0 +00010000 NVC0_COMPUTE.UNK10F4 = { 0x10000 } +00000001 NVC0_COMPUTE.0x10f8 = 0x1 +00002c00 NVC0_COMPUTE.0x10fc = 0x2c00 +200148e3 NVC0_COMPUTE.0x1100 = 0x200148e3 +00000000 NVC0_COMPUTE.0x1104 = 0 +608648e4 NVC0_COMPUTE.0x1108 = 0x608648e4 +00005de4 NVC0_COMPUTE.0x110c = 0x5de4 +28004404 NVC0_COMPUTE.0x1110 = 0x28004404 +94009c04 NVC0_COMPUTE.0x1114 = 0x94009c04 +2c000000 NVC0_COMPUTE.0x1118 = 0x2c000000 +98001c04 NVC0_COMPUTE.0x111c = 0x98001c04 +2c000000 NVC0_COMPUTE.0x1120 = 0x2c000000 +fc1fdc03 NVC0_COMPUTE.0x1124 = 0xfc1fdc03 +207e0000 NVC0_COMPUTE.0x1128 = 0x207e0000 +50001c03 NVC0_COMPUTE.0x112c = 0x50001c03 +20044000 NVC0_COMPUTE.0x1130 = 0x20044000 +a0009de4 NVC0_COMPUTE.0x1134 = 0xa0009de4 +28004000 NVC0_COMPUTE.0x1138 = 0x28004000 +20001e03 NVC0_COMPUTE.0x113c = 0x20001e03 +6000c000 NVC0_COMPUTE.0x1140 = 0x6000c000 +08021c03 NVC0_COMPUTE.0x1144 = 0x8021c03 +6000c000 NVC0_COMPUTE.0x1148 = 0x6000c000 +84001c04 NVC0_COMPUTE.0x114c = 0x84001c04 +2c000000 NVC0_COMPUTE.0x1150 = 0x2c000000 +1080dc03 NVC0_COMPUTE.0x1154 = 0x1080dc03 +2005c000 NVC0_COMPUTE.0x1158 = 0x2005c000 +10809c43 NVC0_COMPUTE.0x115c = 0x10809c43 +5000c000 NVC0_COMPUTE.0x1160 = 0x5000c000 +b0211c43 NVC0_COMPUTE.0x1164 = 0xb0211c43 +48004000 NVC0_COMPUTE.0x1168 = 0x48004000 +0c009c03 NVC0_COMPUTE.0x116c = 0xc009c03 +48010000 NVC0_COMPUTE.0x1170 = 0x48010000 +13f0dc43 NVC0_COMPUTE.0x1174 = 0x13f0dc43 +48000000 NVC0_COMPUTE.0x1178 = 0x48000000 +0021dc05 NVC0_COMPUTE.0x117c = 0x21dc05 +84000000 NVC0_COMPUTE.0x1180 = 0x84000000 +00219c05 NVC0_COMPUTE.0x1184 = 0x219c05 +84000004 NVC0_COMPUTE.0x1188 = 0x84000004 +00215c05 NVC0_COMPUTE.0x118c = 0x215c05 +84000008 NVC0_COMPUTE.0x1190 = 0x84000008 +00211c05 NVC0_COMPUTE.0x1194 = 0x211c05 +8400000c NVC0_COMPUTE.0x1198 = 0x8400000c +0001dc05 NVC0_COMPUTE.0x119c = 0x1dc05 +c9000000 NVC0_COMPUTE.0x11a0 = 0xc9000000 +00019c05 NVC0_COMPUTE.0x11a4 = 0x19c05 +c9000004 NVC0_COMPUTE.0x11a8 = 0xc9000004 +00015c05 NVC0_COMPUTE.0x11ac = 0x15c05 +c9000008 NVC0_COMPUTE.0x11b0 = 0xc9000008 +00011c05 NVC0_COMPUTE.0x11b4 = 0x11c05 +c900000c NVC0_COMPUTE.0x11b8 = 0xc900000c +ffffdc04 NVC0_COMPUTE.0x11bc = 0xffffdc04 +50ee0000 NVC0_COMPUTE.0x11c0 = 0x50ee0000 +00811c03 NVC0_COMPUTE.0x11c4 = 0x811c03 +48010000 NVC0_COMPUTE.0x11c8 = 0x48010000 +80021de4 NVC0_COMPUTE.0x11cc = 0x80021de4 +28004000 NVC0_COMPUTE.0x11d0 = 0x28004000 +08019e03 NVC0_COMPUTE.0x11d4 = 0x8019e03 +6000c000 NVC0_COMPUTE.0x11d8 = 0x6000c000 +fff15c43 NVC0_COMPUTE.0x11dc = 0xfff15c43 +48000000 NVC0_COMPUTE.0x11e0 = 0x48000000 +7841dc03 NVC0_COMPUTE.0x11e4 = 0x7841dc03 +5800c000 NVC0_COMPUTE.0x11e8 = 0x5800c000 +10411c03 NVC0_COMPUTE.0x11ec = 0x10411c03 +2011c000 NVC0_COMPUTE.0x11f0 = 0x2011c000 +0062dc85 NVC0_COMPUTE.0x11f4 = 0x62dc85 +c1000000 NVC0_COMPUTE.0x11f8 = 0xc1000000 +1c515c43 NVC0_COMPUTE.0x11fc = 0x1c515c43 +40000000 NVC0_COMPUTE.0x1200 = 0x40000000 +90515c43 NVC0_COMPUTE.0x1204 = 0x90515c43 +48004000 NVC0_COMPUTE.0x1208 = 0x48004000 +0042dc85 NVC0_COMPUTE.0x120c = 0x42dc85 +94000000 NVC0_COMPUTE.0x1210 = 0x94000000 +00229c05 NVC0_COMPUTE.0x1214 = 0x229c05 +84000010 NVC0_COMPUTE.0x1218 = 0x84000010 +00225c05 NVC0_COMPUTE.0x121c = 0x225c05 +84000014 NVC0_COMPUTE.0x1220 = 0x84000014 +00221c05 NVC0_COMPUTE.0x1224 = 0x221c05 +84000018 NVC0_COMPUTE.0x1228 = 0x84000018 +0021dc05 NVC0_COMPUTE.0x122c = 0x21dc05 +8400001c NVC0_COMPUTE.0x1230 = 0x8400001c +00029c05 NVC0_COMPUTE.LINKED_TSC = 0.000000 +c9000010 NVC0_COMPUTE.0x1238 = 0xc9000010 +00025c05 NVC0_COMPUTE.0x123c = 0x25c05 +c9000014 NVC0_COMPUTE.0x1240 = 0xc9000014 +00021c05 NVC0_COMPUTE.0x1244 = 0x21c05 +c9000018 NVC0_COMPUTE.0x1248 = 0xc9000018 +0001dc05 NVC0_COMPUTE.0x124c = 0x1dc05 +c900001c NVC0_COMPUTE.0x1250 = 0xc900001c +ffffdc04 NVC0_COMPUTE.0x1254 = 0xffffdc04 +50ee0000 NVC0_COMPUTE.0x1258 = 0x50ee0000 +0062dc85 NVC0_COMPUTE.0x125c = 0x62dc85 +c1000010 NVC0_COMPUTE.0x1260 = 0xc1000010 +0042dc85 NVC0_COMPUTE.0x1264 = 0x42dc85 +94000010 NVC0_COMPUTE.0x1268 = 0x94000010 +00229c05 NVC0_COMPUTE.0x126c = 0x229c05 +84000020 NVC0_COMPUTE.0x1270 = 0x84000020 +00225c05 NVC0_COMPUTE.0x1274 = 0x225c05 +84000024 NVC0_COMPUTE.0x1278 = 0x84000024 +00221c05 NVC0_COMPUTE.0x127c = 0x221c05 +84000028 NVC0_COMPUTE.0x1280 = 0x84000028 +0021dc05 NVC0_COMPUTE.0x1284 = 0x21dc05 +8400002c NVC0_COMPUTE.UNK1288_TIC_FLUSH = 0x8400002c +00029c05 NVC0_COMPUTE.0x128c = 0x29c05 +c9000020 NVC0_COMPUTE.0x1290 = 0xc9000020 +00025c05 NVC0_COMPUTE.0x1294 = 0x25c05 +c9000024 NVC0_COMPUTE.0x1298 = 0xc9000024 +00021c05 NVC0_COMPUTE.0x129c = 0x21c05 +c9000028 NVC0_COMPUTE.0x12a0 = 0xc9000028 +0001dc05 NVC0_COMPUTE.0x12a4 = 0x1dc05 +c900002c NVC0_COMPUTE.0x12a8 = 0xc900002c +ffffdc04 NVC0_COMPUTE.UNK12AC = -nan +50ee0000 NVC0_COMPUTE.0x12b0 = 0x50ee0000 +0062dc85 NVC0_COMPUTE.0x12b4 = 0x62dc85 +c1000020 NVC0_COMPUTE.0x12b8 = 0xc1000020 +0042dc85 NVC0_COMPUTE.0x12bc = 0x42dc85 +94000020 NVC0_COMPUTE.0x12c0 = 0x94000020 +00229c05 NVC0_COMPUTE.0x12c4 = 0x229c05 +84000030 NVC0_COMPUTE.0x12c8 = 0x84000030 +00225c05 NVC0_COMPUTE.0x12cc = 0x225c05 +84000034 NVC0_COMPUTE.0x12d0 = 0x84000034 +00221c05 NVC0_COMPUTE.0x12d4 = 0x221c05 +84000038 NVC0_COMPUTE.0x12d8 = 0x84000038 +0021dc05 NVC0_COMPUTE.0x12dc = 0x21dc05 +8400003c NVC0_COMPUTE.0x12e0 = 0x8400003c +00029c05 NVC0_COMPUTE.0x12e4 = 0x29c05 +c9000030 NVC0_COMPUTE.0x12e8 = 0xc9000030 +00025c05 NVC0_COMPUTE.0x12ec = 0x25c05 +c9000034 NVC0_COMPUTE.0x12f0 = 0xc9000034 +00021c05 NVC0_COMPUTE.0x12f4 = 0x21c05 +c9000038 NVC0_COMPUTE.0x12f8 = 0xc9000038 +0001dc05 NVC0_COMPUTE.0x12fc = 0x1dc05 +c900003c NVC0_COMPUTE.0x1300 = 0xc900003c +ffffdc04 NVC0_COMPUTE.0x1304 = 0xffffdc04 +50ee0000 NVC0_COMPUTE.0x1308 = 0x50ee0000 +00601c85 NVC0_COMPUTE.0x130c = 0x601c85 +c1000030 NVC0_COMPUTE.0x1310 = 0xc1000030 +00401c85 NVC0_COMPUTE.0x1314 = 0x401c85 +94000030 NVC0_COMPUTE.0x1318 = 0x94000030 +00001de7 NVC0_COMPUTE.0x131c = 0x1de7 +80000000 NVC0_COMPUTE.0x1320 = 0x80000000 +200446c0 NVC0_COMPUTE.0x1324 = 0x200446c0 +00000000 NVC0_COMPUTE.0x1328 = 0 +0800ffd0 NVC0_COMPUTE.0x132c = 0x800ffd0 +00000034 NVC0_COMPUTE.TSC_FLUSH = { ENTRY = 0x3 | 0x4 } +00000000 NVC0_COMPUTE.TIC_FLUSH = { ENTRY = 0 } +# out of band: 00000198 081059c8 +# out of band: 0000019c 00024a00 +200145a6 NVC0_COMPUTE.TEX_CACHE_CTL = { UNK0 = 0x6 | ENTRY = 0x145a | 0x20000000 } +00000001 NVC0_COMPUTE.0x133c = 0x1 +200446c0 NVC0_COMPUTE.0x1340 = 0x200446c0 +00000000 NVC0_COMPUTE.0x1344 = 0 +0800ffd0 NVC0_COMPUTE.0x1348 = 0x800ffd0 +00000035 NVC0_COMPUTE.0x134c = 0x35 +00000000 NVC0_COMPUTE.0x1350 = 0 +# out of band: 000001a0 08105c10 +# out of band: 000001a4 00001e00 +200348e0 NVC0_COMPUTE.UNK1354 = 0.000000 +00010000 NVC0_COMPUTE.0x1358 = 0x10000 +00000001 NVC0_COMPUTE.0x135c = 0x1 +00002b00 NVC0_COMPUTE.0x1360 = 0x2b00 +200148e3 NVC0_COMPUTE.0x1364 = 0x200148e3 +00000000 NVC0_COMPUTE.0x1368 = 0 +602c48e4 NVC0_COMPUTE.0x136c = 0x602c48e4 +00005de4 NVC0_COMPUTE.0x1370 = 0x5de4 +28004404 NVC0_COMPUTE.0x1374 = 0x28004404 +94009c04 NVC0_COMPUTE.0x1378 = 0x94009c04 +2c000000 NVC0_COMPUTE.0x137c = 0x2c000000 +98001c04 NVC0_COMPUTE.0x1380 = 0x98001c04 +2c000000 NVC0_COMPUTE.0x1384 = 0x2c000000 +10019de2 NVC0_COMPUTE.0x1388 = 0x10019de2 +18000000 NVC0_COMPUTE.0x138c = 0x18000000 +50001c03 NVC0_COMPUTE.0x1390 = 0x50001c03 +20044000 NVC0_COMPUTE.0x1394 = 0x20044000 +84009c04 NVC0_COMPUTE.0x1398 = 0x84009c04 +2c000000 NVC0_COMPUTE.0x139c = 0x2c000000 +20001e03 NVC0_COMPUTE.0x13a0 = 0x20001e03 +6000c000 NVC0_COMPUTE.0x13a4 = 0x6000c000 +08001c43 NVC0_COMPUTE.0x13a8 = 0x8001c43 +40000000 NVC0_COMPUTE.0x13ac = 0x40000000 +1000dc43 NVC0_COMPUTE.0x13b0 = 0x1000dc43 +5000c000 NVC0_COMPUTE.0x13b4 = 0x5000c000 +a0011c03 NVC0_COMPUTE.0x13b8 = 0xa0011c03 +200d8000 NVC0_COMPUTE.0x13bc = 0x200d8000 +b0315c43 NVC0_COMPUTE.0x13c0 = 0xb0315c43 +48004000 NVC0_COMPUTE.0x13c4 = 0x48004000 +80019c03 NVC0_COMPUTE.0x13c8 = 0x80019c03 +200d8000 NVC0_COMPUTE.0x13cc = 0x200d8000 +00409c85 NVC0_COMPUTE.0x13d0 = 0x409c85 +84000000 NVC0_COMPUTE.0x13d4 = 0x84000000 +9031dc43 NVC0_COMPUTE.0x13d8 = 0x9031dc43 +48004000 NVC0_COMPUTE.0x13dc = 0x48004000 +00609c85 NVC0_COMPUTE.0x13e0 = 0x609c85 +94000000 NVC0_COMPUTE.0x13e4 = 0x94000000 +00401c85 NVC0_COMPUTE.0x13e8 = 0x401c85 +84000010 NVC0_COMPUTE.0x13ec = 0x84000010 +00601c85 NVC0_COMPUTE.0x13f0 = 0x601c85 +94000010 NVC0_COMPUTE.0x13f4 = 0x94000010 +00409c85 NVC0_COMPUTE.0x13f8 = 0x409c85 +84000020 NVC0_COMPUTE.0x13fc = 0x84000020 +00609c85 NVC0_COMPUTE.0x1400 = 0x609c85 +94000020 NVC0_COMPUTE.0x1404 = 0x94000020 +00401c85 NVC0_COMPUTE.0x1408 = 0x401c85 +84000030 NVC0_COMPUTE.0x140c = 0x84000030 +00601c85 NVC0_COMPUTE.0x1410 = 0x601c85 +94000030 NVC0_COMPUTE.0x1414 = 0x94000030 +00001de7 NVC0_COMPUTE.0x1418 = 0x1de7 +80000000 NVC0_COMPUTE.0x141c = 0x80000000 +200446c0 NVC0_COMPUTE.0x1420 = 0x200446c0 +00000000 NVC0_COMPUTE.UNK1424_TSC_FLUSH = 0 +0800ffd0 NVC0_COMPUTE.0x1428 = 0x800ffd0 +00000036 NVC0_COMPUTE.0x142c = 0x36 +00000000 NVC0_COMPUTE.0x1430 = 0 +# out of band: 000001a8 08105c2c +# out of band: 000001ac 0000e200 +200145a6 NVC0_COMPUTE.0x1434 = 0x200145a6 +00000001 NVC0_COMPUTE.0x1438 = 0x1 +200446c0 NVC0_COMPUTE.0x143c = 0x200446c0 +00000000 NVC0_COMPUTE.0x1440 = 0 +0800ffd0 NVC0_COMPUTE.0x1444 = 0x800ffd0 +00000037 NVC0_COMPUTE.0x1448 = 0x37 +00000000 NVC0_COMPUTE.0x144c = 0 +# out of band: 000001b0 08105d0c +# out of band: 000001b4 00001e00 +200348e0 NVC0_COMPUTE.0x1450 = 0x200348e0 +00010000 NVC0_COMPUTE.0x1454 = 0x10000 +00000001 NVC0_COMPUTE.0x1458 = 0x1 +00003d00 NVC0_COMPUTE.0x145c = 0x3d00 +200148e3 NVC0_COMPUTE.0x1460 = 0x200148e3 +00000000 NVC0_COMPUTE.0x1464 = 0 +601e48e4 NVC0_COMPUTE.0x1468 = 0x601e48e4 +00005de4 NVC0_COMPUTE.0x146c = 0x5de4 +28004404 NVC0_COMPUTE.0x1470 = 0x28004404 +94001c04 NVC0_COMPUTE.0x1474 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x1478 = 0x2c000000 +84009c04 NVC0_COMPUTE.0x147c = 0x84009c04 +2c000000 NVC0_COMPUTE.0x1480 = 0x2c000000 +20001c03 NVC0_COMPUTE.0x1484 = 0x20001c03 +20044000 NVC0_COMPUTE.0x1488 = 0x20044000 +20001d03 NVC0_COMPUTE.0x148c = 0x20001d03 +48004001 NVC0_COMPUTE.0x1490 = 0x48004001 +c001dc23 NVC0_COMPUTE.0x1494 = 0xc001dc23 +188e4000 NVC0_COMPUTE.0x1498 = 0x188e4000 +fc01dc23 NVC0_COMPUTE.0x149c = 0xfc01dc23 +1b000000 NVC0_COMPUTE.0x14a0 = 0x1b000000 +c000a1e7 NVC0_COMPUTE.0x14a4 = 0xc000a1e7 +40000000 NVC0_COMPUTE.0x14a8 = 0x40000000 +800101e4 NVC0_COMPUTE.0x14ac = 0x800101e4 +28004000 NVC0_COMPUTE.0x14b0 = 0x28004000 +100080e3 NVC0_COMPUTE.0x14b4 = 0x100080e3 +5000c000 NVC0_COMPUTE.0x14b8 = 0x5000c000 +100100a3 NVC0_COMPUTE.0x14bc = 0x100100a3 +2009c000 NVC0_COMPUTE.0x14c0 = 0x2009c000 +a00001e4 NVC0_COMPUTE.0x14c4 = 0xa00001e4 +28004000 NVC0_COMPUTE.0x14c8 = 0x28004000 +90214043 NVC0_COMPUTE.0x14cc = 0x90214043 +48004000 NVC0_COMPUTE.0x14d0 = 0x48004000 +00400085 NVC0_COMPUTE.0x14d4 = 0x400085 +94000000 NVC0_COMPUTE.0x14d8 = 0x94000000 +00001de7 NVC0_COMPUTE.0x14dc = 0x1de7 +80000000 NVC0_COMPUTE.0x14e0 = 0x80000000 +200446c0 NVC0_COMPUTE.0x14e4 = 0x200446c0 +00000000 NVC0_COMPUTE.0x14e8 = 0 +0800ffd0 NVC0_COMPUTE.0x14ec = 0x800ffd0 +00000038 NVC0_COMPUTE.0x14f0 = 0x38 +00000000 NVC0_COMPUTE.0x14f4 = 0 +# out of band: 000001b8 08105d28 +# out of band: 000001bc 0000aa00 +200145a6 NVC0_COMPUTE.0x14f8 = 0x200145a6 +00000001 NVC0_COMPUTE.0x14fc = 0x1 +200446c0 NVC0_COMPUTE.0x1500 = 0x200446c0 +00000000 NVC0_COMPUTE.0x1504 = 0 +0800ffd0 NVC0_COMPUTE.0x1508 = 0x800ffd0 +00000039 NVC0_COMPUTE.0x150c = 0x39 +00000000 NVC0_COMPUTE.0x1510 = 0 +# out of band: 000001c0 08105dd0 +# out of band: 000001c4 00001e00 +200348e0 NVC0_COMPUTE.0x1514 = 0x200348e0 +00010000 NVC0_COMPUTE.0x1518 = 0x10000 +00000001 NVC0_COMPUTE.0x151c = 0x1 +00003b00 NVC0_COMPUTE.0x1520 = 0x3b00 +200148e3 NVC0_COMPUTE.0x1524 = 0x200148e3 +00000000 NVC0_COMPUTE.0x1528 = 0 +604a48e4 NVC0_COMPUTE.0x152c = 0x604a48e4 +00005de4 NVC0_COMPUTE.0x1530 = 0x5de4 +28004404 NVC0_COMPUTE.0x1534 = 0x28004404 +94001c04 NVC0_COMPUTE.0x1538 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x153c = 0x2c000000 +84009c04 NVC0_COMPUTE.0x1540 = 0x84009c04 +2c000000 NVC0_COMPUTE.0x1544 = 0x2c000000 +d0015de4 NVC0_COMPUTE.0x1548 = 0xd0015de4 +28004000 NVC0_COMPUTE.0x154c = 0x28004000 +20001c03 NVC0_COMPUTE.COND_ADDRESS_HIGH = 0x20001c03 +20044000 NVC0_COMPUTE.COND_ADDRESS_LOW = 0x20044000 +98009c04 NVC0_COMPUTE.COND_MODE = 0x98009c04 +2c000000 NVC0_COMPUTE.TSC_ADDRESS_HIGH = 0x2c000000 +2000dd03 NVC0_COMPUTE.TSC_ADDRESS_LOW = 0x2000dd03 +48014001 NVC0_COMPUTE.TSC_LIMIT = 0x48014001 +88001c04 NVC0_COMPUTE.0x1568 = 0x88001c04 +2c000000 NVC0_COMPUTE.0x156c = 0x2c000000 +fff11d43 NVC0_COMPUTE.0x1570 = 0xfff11d43 +48000000 NVC0_COMPUTE.TIC_ADDRESS_HIGH = 0x48000000 +c03fde03 NVC0_COMPUTE.TIC_ADDRESS_LOW = 0xc03fde03 +48014000 NVC0_COMPUTE.TIC_LIMIT = 0x48014000 +30201c03 NVC0_COMPUTE.0x1580 = 0x30201c03 +20004000 NVC0_COMPUTE.0x1584 = 0x20004000 +10009de4 NVC0_COMPUTE.0x1588 = 0x10009de4 +28004001 NVC0_COMPUTE.0x158c = 0x28004001 +1051dc43 NVC0_COMPUTE.0x1590 = 0x1051dc43 +1a0e0000 NVC0_COMPUTE.0x1594 = 0x1a0e0000 +fc3fdd03 NVC0_COMPUTE.0x1598 = 0xfc3fdd03 +48010000 NVC0_COMPUTE.0x159c = 0x48010000 +fc41dc63 NVC0_COMPUTE.0x15a0 = 0xfc41dc63 +1b000000 NVC0_COMPUTE.0x15a4 = 0x1b000000 +000fde03 NVC0_COMPUTE.0x15a8 = 0xfde03 +48014001 NVC0_COMPUTE.0x15ac = 0x48014001 +fc21dc43 NVC0_COMPUTE.0x15b0 = 0xfc21dc43 +1a000000 NVC0_COMPUTE.0x15b4 = 0x1a000000 +000021e7 NVC0_COMPUTE.0x15b8 = 0x21e7 +80000000 NVC0_COMPUTE.0x15bc = 0x80000000 +e0009de4 NVC0_COMPUTE.0x15c0 = 0xe0009de4 +28004000 NVC0_COMPUTE.0x15c4 = 0x28004000 +f0015de4 NVC0_COMPUTE.0x15c8 = 0xf0015de4 +28004000 NVC0_COMPUTE.0x15cc = 0x28004000 +08209c03 NVC0_COMPUTE.0x15d0 = 0x8209c03 +5800c000 NVC0_COMPUTE.0x15d4 = 0x5800c000 +08509fc3 NVC0_COMPUTE.0x15d8 = 0x8509fc3 +40000000 NVC0_COMPUTE.0x15dc = 0x40000000 +08515c03 NVC0_COMPUTE.0x15e0 = 0x8515c03 +5800c000 NVC0_COMPUTE.0x15e4 = 0x5800c000 +0801dc03 NVC0_COMPUTE.0x15e8 = 0x801dc03 +50010000 NVC0_COMPUTE.0x15ec = 0x50010000 +08019c43 NVC0_COMPUTE.0x15f0 = 0x8019c43 +20ff0000 NVC0_COMPUTE.0x15f4 = 0x20ff0000 +0bf19c03 NVC0_COMPUTE.0x15f8 = 0xbf19c03 +208c0000 NVC0_COMPUTE.0x15fc = 0x208c0000 +1c309c03 NVC0_COMPUTE.0x1600 = 0x1c309c03 +48010000 NVC0_COMPUTE.0x1604 = 0x48010000 +14001c03 NVC0_COMPUTE.CODE_ADDRESS_HIGH = 0x14001c03 +200c0000 NVC0_COMPUTE.CODE_ADDRESS_LOW = 0x200c0000 +80015de4 NVC0_COMPUTE.0x1610 = 0x80015de4 +28004000 NVC0_COMPUTE.0x1614 = 0x28004000 +7820dc03 NVC0_COMPUTE.0x1618 = 0x7820dc03 +5800c000 NVC0_COMPUTE.0x161c = 0x5800c000 +00401c43 NVC0_COMPUTE.0x1620 = 0x401c43 +48000000 NVC0_COMPUTE.0x1624 = 0x48000000 +10209c03 NVC0_COMPUTE.0x1628 = 0x10209c03 +200bc000 NVC0_COMPUTE.0x162c = 0x200bc000 +a0011de4 NVC0_COMPUTE.0x1630 = 0xa0011de4 +28004000 NVC0_COMPUTE.0x1634 = 0x28004000 +0c001c43 NVC0_COMPUTE.0x1638 = 0xc001c43 +40000000 NVC0_COMPUTE.0x163c = 0x40000000 +9000dc43 NVC0_COMPUTE.0x1640 = 0x9000dc43 +48004000 NVC0_COMPUTE.0x1644 = 0x48004000 +00211c85 NVC0_COMPUTE.0x1648 = 0x211c85 +94000000 NVC0_COMPUTE.0x164c = 0x94000000 +00001de7 NVC0_COMPUTE.0x1650 = 0x1de7 +80000000 NVC0_COMPUTE.0x1654 = 0x80000000 +200446c0 NVC0_COMPUTE.0x1658 = 0x200446c0 +00000000 NVC0_COMPUTE.0x165c = 0 +0800ffd0 NVC0_COMPUTE.0x1660 = 0x800ffd0 +0000003a NVC0_COMPUTE.TEX_MISC = { SEAMLESS_CUBE_MAP | 0x38 } +00000000 NVC0_COMPUTE.0x1668 = 0 +# out of band: 000001c8 08105dec +# out of band: 000001cc 00015a00 +200145a6 NVC0_COMPUTE.0x166c = 0x200145a6 +00000001 NVC0_COMPUTE.0x1670 = 0x1 +200446c0 NVC0_COMPUTE.0x1674 = 0x200446c0 +00000000 NVC0_COMPUTE.0x1678 = 0 +0800ffd0 NVC0_COMPUTE.0x167c = 0x800ffd0 +0000003b NVC0_COMPUTE.0x1680 = 0x3b +00000000 NVC0_COMPUTE.0x1684 = 0 +# out of band: 000001d0 08105f44 +# out of band: 000001d4 00001e00 +200348e0 NVC0_COMPUTE.0x1688 = 0x200348e0 +00010000 NVC0_COMPUTE.0x168c = 0x10000 +00000001 NVC0_COMPUTE.UNK1690 = { ALWAYS_DERIV } +00003800 NVC0_COMPUTE.CB_BIND = { INDEX = 24 | 0x2000 } +200148e3 NVC0_COMPUTE.FLUSH = { CODE | 0x200148e2 } +00000000 NVC0_COMPUTE.0x169c = 0 +609a48e4 NVC0_COMPUTE.0x16a0 = 0x609a48e4 +00005de4 NVC0_COMPUTE.0x16a4 = 0x5de4 +28004404 NVC0_COMPUTE.0x16a8 = 0x28004404 +9800dc04 NVC0_COMPUTE.0x16ac = 0x9800dc04 +2c000000 NVC0_COMPUTE.0x16b0 = 0x2c000000 +88009c04 NVC0_COMPUTE.0x16b4 = 0x88009c04 +2c000000 NVC0_COMPUTE.0x16b8 = 0x2c000000 +94001c04 NVC0_COMPUTE.0x16bc = 0x94001c04 +2c000000 NVC0_COMPUTE.0x16c0 = 0x2c000000 +10011de4 NVC0_COMPUTE.0x16c4 = 0x10011de4 +28004001 NVC0_COMPUTE.0x16c8 = 0x28004001 +3030dc03 NVC0_COMPUTE.0x16cc = 0x3030dc03 +20044000 NVC0_COMPUTE.0x16d0 = 0x20044000 +84009c04 NVC0_COMPUTE.0x16d4 = 0x84009c04 +2c000000 NVC0_COMPUTE.0x16d8 = 0x2c000000 +003fde03 NVC0_COMPUTE.0x16dc = 0x3fde03 +48014001 NVC0_COMPUTE.0x16e0 = 0x48014001 +20001c03 NVC0_COMPUTE.0x16e4 = 0x20001c03 +20044000 NVC0_COMPUTE.0x16e8 = 0x20044000 +fc41dc43 NVC0_COMPUTE.0x16ec = 0xfc41dc43 +198e0000 NVC0_COMPUTE.0x16f0 = 0x198e0000 +20015d03 NVC0_COMPUTE.0x16f4 = 0x20015d03 +48014001 NVC0_COMPUTE.0x16f8 = 0x48014001 +c0001de4 NVC0_COMPUTE.0x16fc = 0xc0001de4 +28004000 NVC0_COMPUTE.0x1700 = 0x28004000 +d0011de4 NVC0_COMPUTE.0x1704 = 0xd0011de4 +28004000 NVC0_COMPUTE.0x1708 = 0x28004000 +fff19d43 NVC0_COMPUTE.0x170c = 0xfff19d43 +48000000 NVC0_COMPUTE.0x1710 = 0x48000000 +000001e7 NVC0_COMPUTE.0x1714 = 0x1e7 +80000000 NVC0_COMPUTE.0x1718 = 0x80000000 +e0009de4 NVC0_COMPUTE.0x171c = 0xe0009de4 +28004000 NVC0_COMPUTE.0x1720 = 0x28004000 +f001dde4 NVC0_COMPUTE.0x1724 = 0xf001dde4 +28004000 NVC0_COMPUTE.0x1728 = 0x28004000 +04209c03 NVC0_COMPUTE.0x172c = 0x4209c03 +5800c000 NVC0_COMPUTE.0x1730 = 0x5800c000 +08709fe3 NVC0_COMPUTE.0x1734 = 0x8709fe3 +40000000 NVC0_COMPUTE.0x1738 = 0x40000000 +0471dc03 NVC0_COMPUTE.0x173c = 0x471dc03 +5800c000 NVC0_COMPUTE.0x1740 = 0x5800c000 +0c221c03 NVC0_COMPUTE.0x1744 = 0xc221c03 +50010000 NVC0_COMPUTE.0x1748 = 0x50010000 +0c209c43 NVC0_COMPUTE.0x174c = 0xc209c43 +20ff0000 NVC0_COMPUTE.0x1750 = 0x20ff0000 +0c70dc03 NVC0_COMPUTE.0x1754 = 0xc70dc03 +20840000 NVC0_COMPUTE.0x1758 = 0x20840000 +20809c03 NVC0_COMPUTE.0x175c = 0x20809c03 +48010000 NVC0_COMPUTE.0x1760 = 0x48010000 +0c30dc43 NVC0_COMPUTE.0x1764 = 0xc30dc43 +48000000 NVC0_COMPUTE.0x1768 = 0x48000000 +80209c03 NVC0_COMPUTE.0x176c = 0x80209c03 +48014000 NVC0_COMPUTE.0x1770 = 0x48014000 +0821dc03 NVC0_COMPUTE.0x1774 = 0x821dc03 +6800c000 NVC0_COMPUTE.0x1778 = 0x6800c000 +03f21c04 NVC0_COMPUTE.0x177c = 0x3f21c04 +3000c3c0 NVC0_COMPUTE.0x1780 = 0x3000c3c0 +fc7fdd03 NVC0_COMPUTE.0x1784 = 0xfc7fdd03 +48010000 NVC0_COMPUTE.0x1788 = 0x48010000 +fff1dc43 NVC0_COMPUTE.0x178c = 0xfff1dc43 +190e0000 NVC0_COMPUTE.0x1790 = 0x190e0000 +00801c04 NVC0_COMPUTE.0x1794 = 0x801c04 +3400c3c0 NVC0_COMPUTE.0x1798 = 0x3400c3c0 +9030dc43 NVC0_COMPUTE.0x179c = 0x9030dc43 +48004000 NVC0_COMPUTE.0x17a0 = 0x48004000 +800001e7 NVC0_COMPUTE.0x17a4 = 0x800001e7 +40000001 NVC0_COMPUTE.0x17a8 = 0x40000001 +fc5fdd03 NVC0_COMPUTE.0x17ac = 0xfc5fdd03 +4801ffff NVC0_COMPUTE.0x17b0 = 0x4801ffff +fc011de2 NVC0_COMPUTE.0x17b4 = 0xfc011de2 +1bffffff NVC0_COMPUTE.0x17b8 = 0x1bffffff +fc61dc63 NVC0_COMPUTE.0x17bc = 0xfc61dc63 +1a8effff NVC0_COMPUTE.0x17c0 = 0x1a8effff +c0401c03 NVC0_COMPUTE.0x17c4 = 0xc0401c03 +48014000 NVC0_COMPUTE.0x17c8 = 0x48014000 +a111e084 NVC0_COMPUTE.0x17cc = 0xa111e084 +1c004000 NVC0_COMPUTE.0x17d0 = 0x1c004000 +d0411c43 NVC0_COMPUTE.0x17d4 = 0xd0411c43 +48004000 NVC0_COMPUTE.0x17d8 = 0x48004000 +fc0fdd03 NVC0_COMPUTE.0x17dc = 0xfc0fdd03 +48010000 NVC0_COMPUTE.0x17e0 = 0x48010000 +0021e065 NVC0_COMPUTE.0x17e4 = 0x21e065 +94000000 NVC0_COMPUTE.0x17e8 = 0x94000000 +fc41dc43 NVC0_COMPUTE.0x17ec = 0xfc41dc43 +1a8e0000 NVC0_COMPUTE.0x17f0 = 0x1a8e0000 +08209c03 NVC0_COMPUTE.0x17f4 = 0x8209c03 +4801c000 NVC0_COMPUTE.0x17f8 = 0x4801c000 +fc30dc43 NVC0_COMPUTE.0x17fc = 0xfc30dc43 +48000000 NVC0_COMPUTE.0x1800 = 0x48000000 +000021e7 NVC0_COMPUTE.0x1804 = 0x21e7 +80000000 NVC0_COMPUTE.0x1808 = 0x80000000 +1451dc03 NVC0_COMPUTE.0x180c = 0x1451dc03 +48010000 NVC0_COMPUTE.0x1810 = 0x48010000 +18621c43 NVC0_COMPUTE.0x1814 = 0x18621c43 +48000000 NVC0_COMPUTE.0x1818 = 0x48000000 +fc025c03 NVC0_COMPUTE.0x181c = 0xfc025c03 +4801ffff NVC0_COMPUTE.0x1820 = 0x4801ffff +fc429c43 NVC0_COMPUTE.0x1824 = 0xfc429c43 +4800ffff NVC0_COMPUTE.0x1828 = 0x4800ffff +247fdd03 NVC0_COMPUTE.0x182c = 0x247fdd03 +48010000 NVC0_COMPUTE.0x1830 = 0x48010000 +2881dc43 NVC0_COMPUTE.0x1834 = 0x2881dc43 +188e0000 NVC0_COMPUTE.0x1838 = 0x188e0000 +fc5fdd03 NVC0_COMPUTE.0x183c = 0xfc5fdd03 +48010000 NVC0_COMPUTE.0x1840 = 0x48010000 +fc61dc63 NVC0_COMPUTE.0x1844 = 0xfc61dc63 +1b000000 NVC0_COMPUTE.0x1848 = 0x1b000000 +2000a1e7 NVC0_COMPUTE.0x184c = 0x2000a1e7 +40000001 NVC0_COMPUTE.0x1850 = 0x40000001 +a00281e4 NVC0_COMPUTE.0x1854 = 0xa00281e4 +28004000 NVC0_COMPUTE.0x1858 = 0x28004000 +78524003 NVC0_COMPUTE.0x185c = 0x78524003 +5800c000 NVC0_COMPUTE.0x1860 = 0x5800c000 +10520003 NVC0_COMPUTE.0x1864 = 0x10520003 +2005c000 NVC0_COMPUTE.0x1868 = 0x2005c000 +fca1c003 NVC0_COMPUTE.0x186c = 0xfca1c003 +6800c3ff NVC0_COMPUTE.0x1870 = 0x6800c3ff +40a28003 NVC0_COMPUTE.0x1874 = 0x40a28003 +6000c000 NVC0_COMPUTE.0x1878 = 0x6000c000 +24624043 NVC0_COMPUTE.0x187c = 0x24624043 +40000000 NVC0_COMPUTE.0x1880 = 0x40000000 +28728043 NVC0_COMPUTE.0x1884 = 0x28728043 +68000000 NVC0_COMPUTE.0x1888 = 0x68000000 +24324043 NVC0_COMPUTE.0x188c = 0x24324043 +48000000 NVC0_COMPUTE.0x1890 = 0x48000000 +00828085 NVC0_COMPUTE.0x1894 = 0x828085 +94000000 NVC0_COMPUTE.0x1898 = 0x94000000 +00001c03 NVC0_COMPUTE.0x189c = 0x1c03 +48010000 NVC0_COMPUTE.0x18a0 = 0x48010000 +10411c43 NVC0_COMPUTE.0x18a4 = 0x10411c43 +48000000 NVC0_COMPUTE.0x18a8 = 0x48000000 +08009c03 NVC0_COMPUTE.0x18ac = 0x8009c03 +48010000 NVC0_COMPUTE.0x18b0 = 0x48010000 +08201c03 NVC0_COMPUTE.0x18b4 = 0x8201c03 +6800c000 NVC0_COMPUTE.0x18b8 = 0x6800c000 +03f1dc04 NVC0_COMPUTE.0x18bc = 0x3f1dc04 +3000c3c0 NVC0_COMPUTE.0x18c0 = 0x3000c3c0 +fc0fdd03 NVC0_COMPUTE.0x18c4 = 0xfc0fdd03 +48010000 NVC0_COMPUTE.0x18c8 = 0x48010000 +fff1dc43 NVC0_COMPUTE.0x18cc = 0xfff1dc43 +1a8e0000 NVC0_COMPUTE.0x18d0 = 0x1a8e0000 +fc5fdd03 NVC0_COMPUTE.0x18d4 = 0xfc5fdd03 +48010000 NVC0_COMPUTE.0x18d8 = 0x48010000 +fc61dc63 NVC0_COMPUTE.0x18dc = 0xfc61dc63 +19000000 NVC0_COMPUTE.0x18e0 = 0x19000000 +00701c04 NVC0_COMPUTE.0x18e4 = 0x701c04 +3400c3c0 NVC0_COMPUTE.0x18e8 = 0x3400c3c0 +0c40dc43 NVC0_COMPUTE.0x18ec = 0xc40dc43 +48000000 NVC0_COMPUTE.0x18f0 = 0x48000000 +a1100084 NVC0_COMPUTE.0x18f4 = 0xa1100084 +1c004000 NVC0_COMPUTE.0x18f8 = 0x1c004000 +f8200065 NVC0_COMPUTE.0x18fc = 0xf8200065 +97ffffff NVC0_COMPUTE.0x1900 = 0x97ffffff +00001de7 NVC0_COMPUTE.0x1904 = 0x1de7 +80000000 NVC0_COMPUTE.0x1908 = 0x80000000 +200446c0 NVC0_COMPUTE.0x190c = 0x200446c0 +00000000 NVC0_COMPUTE.0x1910 = 0 +0800ffd0 NVC0_COMPUTE.0x1914 = 0x800ffd0 +0000003c NVC0_COMPUTE.0x1918 = 0x3c +00000000 NVC0_COMPUTE.0x191c = 0 +# out of band: 000001d8 08105f60 +# out of band: 000001dc 00029a00 +200145a6 NVC0_COMPUTE.0x1920 = 0x200145a6 +00000001 NVC0_COMPUTE.0x1924 = 0x1 +200446c0 NVC0_COMPUTE.0x1928 = 0x200446c0 +00000000 NVC0_COMPUTE.0x192c = 0 +0800ffd0 NVC0_COMPUTE.UNK1930 = 0.000000 +0000003d NVC0_COMPUTE.0x1934 = 0x3d +00000000 NVC0_COMPUTE.0x1938 = 0 +# out of band: 000001e0 081061f8 +# out of band: 000001e4 00001e00 +200348e0 NVC0_COMPUTE.0x193c = 0x200348e0 +00010000 NVC0_COMPUTE.0x1940 = 0x10000 +00000001 NVC0_COMPUTE.UNK1944 = 0x1 +00003500 NVC0_COMPUTE.0x1948 = 0x3500 +200148e3 NVC0_COMPUTE.0x194c = 0x200148e3 +00000000 NVC0_COMPUTE.0x1950 = 0 +60ae48e4 NVC0_COMPUTE.0x1954 = 0x60ae48e4 +00005de4 NVC0_COMPUTE.0x1958 = 0x5de4 +28004404 NVC0_COMPUTE.0x195c = 0x28004404 +9800dc04 NVC0_COMPUTE.0x1960 = 0x9800dc04 +2c000000 NVC0_COMPUTE.0x1964 = 0x2c000000 +88009c04 NVC0_COMPUTE.0x1968 = 0x88009c04 +2c000000 NVC0_COMPUTE.0x196c = 0x2c000000 +94001c04 NVC0_COMPUTE.0x1970 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x1974 = 0x2c000000 +10011de4 NVC0_COMPUTE.0x1978 = 0x10011de4 +28004001 NVC0_COMPUTE.0x197c = 0x28004001 +3030dc03 NVC0_COMPUTE.0x1980 = 0x3030dc03 +20044000 NVC0_COMPUTE.0x1984 = 0x20044000 +84009c04 NVC0_COMPUTE.0x1988 = 0x84009c04 +2c000000 NVC0_COMPUTE.0x198c = 0x2c000000 +003fde03 NVC0_COMPUTE.0x1990 = 0x3fde03 +48014001 NVC0_COMPUTE.0x1994 = 0x48014001 +20001c03 NVC0_COMPUTE.0x1998 = 0x20001c03 +20044000 NVC0_COMPUTE.0x199c = 0x20044000 +fc41dc43 NVC0_COMPUTE.0x19a0 = 0xfc41dc43 +198e0000 NVC0_COMPUTE.0x19a4 = 0x198e0000 +20019d03 NVC0_COMPUTE.0x19a8 = 0x20019d03 +48014001 NVC0_COMPUTE.0x19ac = 0x48014001 +fff1dd43 NVC0_COMPUTE.0x19b0 = 0xfff1dd43 +48000000 NVC0_COMPUTE.0x19b4 = 0x48000000 +000001e7 NVC0_COMPUTE.0x19b8 = 0x1e7 +80000000 NVC0_COMPUTE.0x19bc = 0x80000000 +e0309c03 NVC0_COMPUTE.0x19c0 = 0xe0309c03 +50014000 NVC0_COMPUTE.0x19c4 = 0x50014000 +80000007 NVC0_COMPUTE.0x19c8 = 0x80000007 +60000003 NVC0_COMPUTE.0x19cc = 0x60000003 +e0301c43 NVC0_COMPUTE.0x19d0 = 0xe0301c43 +20ff4000 NVC0_COMPUTE.0x19d4 = 0x20ff4000 +f0311c03 NVC0_COMPUTE.0x19d8 = 0xf0311c03 +20804000 NVC0_COMPUTE.0x19dc = 0x20804000 +80201c03 NVC0_COMPUTE.0x19e0 = 0x80201c03 +48014000 NVC0_COMPUTE.0x19e4 = 0x48014000 +0c009c03 NVC0_COMPUTE.0x19e8 = 0xc009c03 +6800c000 NVC0_COMPUTE.0x19ec = 0x6800c000 +03f15c04 NVC0_COMPUTE.0x19f0 = 0x3f15c04 +3000c3c0 NVC0_COMPUTE.0x19f4 = 0x3000c3c0 +10209e03 NVC0_COMPUTE.0x19f8 = 0x10209e03 +4800c000 NVC0_COMPUTE.0x19fc = 0x4800c000 +0c20dc03 NVC0_COMPUTE.0x1a00 = 0xc20dc03 +6800c000 NVC0_COMPUTE.0x1a04 = 0x6800c000 +c03fdd03 NVC0_COMPUTE.0x1a08 = 0xc03fdd03 +48014000 NVC0_COMPUTE.0x1a0c = 0x48014000 +d3f3dc43 NVC0_COMPUTE.0x1a10 = 0xd3f3dc43 +1b0e4000 NVC0_COMPUTE.0x1a14 = 0x1b0e4000 +fc6fdd03 NVC0_COMPUTE.0x1a18 = 0xfc6fdd03 +48010000 NVC0_COMPUTE.0x1a1c = 0x48010000 +fc71dc63 NVC0_COMPUTE.0x1a20 = 0xfc71dc63 +190e0000 NVC0_COMPUTE.DELAY = 0x190e0000 +00501c04 NVC0_COMPUTE.0x1a28 = 0x501c04 +3400c3c0 NVC0_COMPUTE.UNK1A2C[0] = 0x3400c3c0 +90409c43 NVC0_COMPUTE.UNK1A2C[0x1] = 0x90409c43 +48004000 NVC0_COMPUTE.UNK1A2C[0x2] = 0x48004000 +c000c5e4 NVC0_COMPUTE.UNK1A2C[0x3] = 0xc000c5e4 +28004000 NVC0_COMPUTE.UNK1A2C[0x4] = 0x28004000 +800021e7 NVC0_COMPUTE.0x1a40 = 0x800021e7 +40000001 NVC0_COMPUTE.0x1a44 = 0x40000001 +fc33dc03 NVC0_COMPUTE.0x1a48 = 0xfc33dc03 +190e0000 NVC0_COMPUTE.0x1a4c = 0x190e0000 +400005e7 NVC0_COMPUTE.0x1a50 = 0x400005e7 +40000001 NVC0_COMPUTE.0x1a54 = 0x40000001 +00021de4 NVC0_COMPUTE.0x1a58 = 0x21de4 +28000000 NVC0_COMPUTE.0x1a5c = 0x28000000 +08025de4 NVC0_COMPUTE.0x1a60 = 0x8025de4 +28000000 NVC0_COMPUTE.0x1a64 = 0x28000000 +fc011de4 NVC0_COMPUTE.0x1a68 = 0xfc011de4 +28000000 NVC0_COMPUTE.0x1a6c = 0x28000000 +a1015c84 NVC0_COMPUTE.0x1a70 = 0xa1015c84 +1c004000 NVC0_COMPUTE.0x1a74 = 0x1c004000 +00815c25 NVC0_COMPUTE.0x1a78 = 0x815c25 +94000000 NVC0_COMPUTE.0x1a7c = 0x94000000 +04411c03 NVC0_COMPUTE.0x1a80 = 0x4411c03 +4800c000 NVC0_COMPUTE.0x1a84 = 0x4800c000 +04821c03 NVC0_COMPUTE.0x1a88 = 0x4821c03 +4801c000 NVC0_COMPUTE.0x1a8c = 0x4801c000 +0c43dc03 NVC0_COMPUTE.0x1a90 = 0xc43dc03 +1a8e0000 NVC0_COMPUTE.0x1a94 = 0x1a8e0000 +fc925c43 NVC0_COMPUTE.0x1a98 = 0xfc925c43 +48000000 NVC0_COMPUTE.0x1a9c = 0x48000000 +400005e7 NVC0_COMPUTE.0x1aa0 = 0x400005e7 +4003ffff NVC0_COMPUTE.0x1aa4 = 0x4003ffff +c0311e13 NVC0_COMPUTE.0x1aa8 = 0xc0311e13 +48014000 NVC0_COMPUTE.0x1aac = 0x48014000 +d3f15e43 NVC0_COMPUTE.0x1ab0 = 0xd3f15e43 +48004000 NVC0_COMPUTE.0x1ab4 = 0x48004000 +fc4fdd03 NVC0_COMPUTE.0x1ab8 = 0xfc4fdd03 +48010000 NVC0_COMPUTE.0x1abc = 0x48010000 +fc53dc43 NVC0_COMPUTE.0x1ac0 = 0xfc53dc43 +1a8e0000 NVC0_COMPUTE.0x1ac4 = 0x1a8e0000 +000025e7 NVC0_COMPUTE.0x1ac8 = 0x25e7 +80000000 NVC0_COMPUTE.0x1acc = 0x80000000 +f0421c03 NVC0_COMPUTE.0x1ad0 = 0xf0421c03 +6800ffff NVC0_COMPUTE.0x1ad4 = 0x6800ffff +78625c03 NVC0_COMPUTE.0x1ad8 = 0x78625c03 +5800c000 NVC0_COMPUTE.0x1adc = 0x5800c000 +206fdc43 NVC0_COMPUTE.0x1ae0 = 0x206fdc43 +40810000 NVC0_COMPUTE.0x1ae4 = 0x40810000 +24721c43 NVC0_COMPUTE.0x1ae8 = 0x24721c43 +40000000 NVC0_COMPUTE.0x1aec = 0x40000000 +1483dc43 NVC0_COMPUTE.0x1af0 = 0x1483dc43 +188e0000 NVC0_COMPUTE.0x1af4 = 0x188e0000 +fc6fdd03 NVC0_COMPUTE.0x1af8 = 0xfc6fdd03 +48010000 NVC0_COMPUTE.0x1afc = 0x48010000 +fc73dc63 NVC0_COMPUTE.QUERY_ADDRESS_HIGH = 0xfc73dc63 +1b020000 NVC0_COMPUTE.QUERY_ADDRESS_LOW = 0x1b020000 +a000a5e7 NVC0_COMPUTE.QUERY_SEQUENCE = 0xa000a5e7 +40000001 NVC0_COMPUTE.QUERY_GET = { MODE = 0x1 | 0x40000000 } +a00205e4 NVC0_COMPUTE.0x1b10 = 0xa00205e4 +28004000 NVC0_COMPUTE.0x1b14 = 0x28004000 +7862c403 NVC0_COMPUTE.0x1b18 = 0x7862c403 +5800c000 NVC0_COMPUTE.0x1b1c = 0x5800c000 +00328403 NVC0_COMPUTE.0x1b20 = 0x328403 +48010000 NVC0_COMPUTE.0x1b24 = 0x48010000 +fc820403 NVC0_COMPUTE.0x1b28 = 0xfc820403 +6800c003 NVC0_COMPUTE.0x1b2c = 0x6800c003 +2c71c443 NVC0_COMPUTE.0x1b30 = 0x2c71c443 +40000000 NVC0_COMPUTE.0x1b34 = 0x40000000 +0bf2c443 NVC0_COMPUTE.0x1b38 = 0xbf2c443 +48000000 NVC0_COMPUTE.0x1b3c = 0x48000000 +20824403 NVC0_COMPUTE.0x1b40 = 0x20824403 +6000c000 NVC0_COMPUTE.0x1b44 = 0x6000c000 +10618403 NVC0_COMPUTE.0x1b48 = 0x10618403 +2015c000 NVC0_COMPUTE.0x1b4c = 0x2015c000 +20920443 NVC0_COMPUTE.0x1b50 = 0x20920443 +68000000 NVC0_COMPUTE.0x1b54 = 0x68000000 +1cb1c443 NVC0_COMPUTE.0x1b58 = 0x1cb1c443 +48000000 NVC0_COMPUTE.0x1b5c = 0x48000000 +40824403 NVC0_COMPUTE.0x1b60 = 0x40824403 +6000c000 NVC0_COMPUTE.0x1b64 = 0x6000c000 +24820443 NVC0_COMPUTE.0x1b68 = 0x24820443 +68000000 NVC0_COMPUTE.0x1b6c = 0x68000000 +00620485 NVC0_COMPUTE.0x1b70 = 0x620485 +94000000 NVC0_COMPUTE.0x1b74 = 0x94000000 +c0019c03 NVC0_COMPUTE.0x1b78 = 0xc0019c03 +48004000 NVC0_COMPUTE.0x1b7c = 0x48004000 +0c619c03 NVC0_COMPUTE.0x1b80 = 0xc619c03 +6800c000 NVC0_COMPUTE.0x1b84 = 0x6800c000 +fc63dc03 NVC0_COMPUTE.0x1b88 = 0xfc63dc03 +190e0000 NVC0_COMPUTE.0x1b8c = 0x190e0000 +000005e7 NVC0_COMPUTE.0x1b90 = 0x5e7 +80000000 NVC0_COMPUTE.0x1b94 = 0x80000000 +0030dc03 NVC0_COMPUTE.0x1b98 = 0x30dc03 +48010000 NVC0_COMPUTE.0x1b9c = 0x48010000 +fc001de4 NVC0_COMPUTE.0x1ba0 = 0xfc001de4 +28000000 NVC0_COMPUTE.0x1ba4 = 0x28000000 +0bf1dc43 NVC0_COMPUTE.0x1ba8 = 0xbf1dc43 +48000000 NVC0_COMPUTE.0x1bac = 0x48000000 +e000a1e7 NVC0_COMPUTE.0x1bb0 = 0xe000a1e7 +40000000 NVC0_COMPUTE.0x1bb4 = 0x40000000 +7c008023 NVC0_COMPUTE.0x1bb8 = 0x7c008023 +7000c004 NVC0_COMPUTE.0x1bbc = 0x7000c004 +00420103 NVC0_COMPUTE.0x1bc0 = 0x420103 +48010000 NVC0_COMPUTE.0x1bc4 = 0x48010000 +08524143 NVC0_COMPUTE.0x1bc8 = 0x8524143 +48000000 NVC0_COMPUTE.0x1bcc = 0x48000000 +20320003 NVC0_COMPUTE.0x1bd0 = 0x20320003 +48010000 NVC0_COMPUTE.0x1bd4 = 0x48010000 +a1008084 NVC0_COMPUTE.0x1bd8 = 0xa1008084 +1c004000 NVC0_COMPUTE.0x1bdc = 0x1c004000 +24724043 NVC0_COMPUTE.0x1be0 = 0x24724043 +48000000 NVC0_COMPUTE.0x1be4 = 0x48000000 +fc808025 NVC0_COMPUTE.0x1be8 = 0xfc808025 +97ffffff NVC0_COMPUTE.0x1bec = 0x97ffffff +04001c03 NVC0_COMPUTE.0x1bf0 = 0x4001c03 +4800c000 NVC0_COMPUTE.0x1bf4 = 0x4800c000 +1803dc03 NVC0_COMPUTE.0x1bf8 = 0x1803dc03 +1a8e0000 NVC0_COMPUTE.0x1bfc = 0x1a8e0000 +a00005e7 NVC0_COMPUTE.0x1c00 = 0xa00005e7 +4003fffe NVC0_COMPUTE.0x1c04 = 0x4003fffe +00001de7 NVC0_COMPUTE.0x1c08 = 0x1de7 +80000000 NVC0_COMPUTE.0x1c0c = 0x80000000 +200446c0 NVC0_COMPUTE.0x1c10 = 0x200446c0 +00000000 NVC0_COMPUTE.0x1c14 = 0 +0800ffd0 NVC0_COMPUTE.0x1c18 = 0x800ffd0 +0000003e NVC0_COMPUTE.0x1c1c = 0x3e +00000000 NVC0_COMPUTE.0x1c20 = 0 +# out of band: 000001e8 08106214 +# out of band: 000001ec 0002ea00 +200145a6 NVC0_COMPUTE.0x1c24 = 0x200145a6 +00000001 NVC0_COMPUTE.0x1c28 = 0x1 +200446c0 NVC0_COMPUTE.0x1c2c = 0x200446c0 +00000000 NVC0_COMPUTE.0x1c30 = 0 +0800ffd0 NVC0_COMPUTE.0x1c34 = 0x800ffd0 +0000003f NVC0_COMPUTE.0x1c38 = 0x3f +00000000 NVC0_COMPUTE.0x1c3c = 0 +# out of band: 000001f0 081064fc +# out of band: 000001f4 00001e00 +200348e0 NVC0_COMPUTE.0x1c40 = 0x200348e0 +00010000 NVC0_COMPUTE.0x1c44 = 0x10000 +00000001 NVC0_COMPUTE.0x1c48 = 0x1 +00004400 NVC0_COMPUTE.0x1c4c = 0x4400 +200148e3 NVC0_COMPUTE.0x1c50 = 0x200148e3 +00000000 NVC0_COMPUTE.0x1c54 = 0 +603a48e4 NVC0_COMPUTE.0x1c58 = 0x603a48e4 +00005de4 NVC0_COMPUTE.0x1c5c = 0x5de4 +28004404 NVC0_COMPUTE.0x1c60 = 0x28004404 +94001c04 NVC0_COMPUTE.0x1c64 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x1c68 = 0x2c000000 +84009c04 NVC0_COMPUTE.0x1c6c = 0x84009c04 +2c000000 NVC0_COMPUTE.0x1c70 = 0x2c000000 +08001cc3 NVC0_COMPUTE.0x1c74 = 0x8001cc3 +40000000 NVC0_COMPUTE.0x1c78 = 0x40000000 +d0009de4 NVC0_COMPUTE.0x1c7c = 0xd0009de4 +28004000 NVC0_COMPUTE.0x1c80 = 0x28004000 +c00fde03 NVC0_COMPUTE.0x1c84 = 0xc00fde03 +48014000 NVC0_COMPUTE.0x1c88 = 0x48014000 +fc21dc43 NVC0_COMPUTE.0x1c8c = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0x1c90 = 0x198e0000 +e00001e7 NVC0_COMPUTE.0x1c94 = 0xe00001e7 +40000000 NVC0_COMPUTE.0x1c98 = 0x40000000 +8000dde4 NVC0_COMPUTE.0x1c9c = 0x8000dde4 +28004000 NVC0_COMPUTE.0x1ca0 = 0x28004000 +78009c03 NVC0_COMPUTE.0x1ca4 = 0x78009c03 +5800c000 NVC0_COMPUTE.0x1ca8 = 0x5800c000 +10011c03 NVC0_COMPUTE.0x1cac = 0x10011c03 +2007c000 NVC0_COMPUTE.0x1cb0 = 0x2007c000 +a0001de4 NVC0_COMPUTE.0x1cb4 = 0xa0001de4 +28004000 NVC0_COMPUTE.0x1cb8 = 0x28004000 +90215c43 NVC0_COMPUTE.0x1cbc = 0x90215c43 +48004000 NVC0_COMPUTE.0x1cc0 = 0x48004000 +00401c85 NVC0_COMPUTE.0x1cc4 = 0x401c85 +94000000 NVC0_COMPUTE.0x1cc8 = 0x94000000 +a0001de7 NVC0_COMPUTE.0x1ccc = 0xa0001de7 +40000001 NVC0_COMPUTE.0x1cd0 = 0x40000001 +000fde03 NVC0_COMPUTE.0x1cd4 = 0xfde03 +48014001 NVC0_COMPUTE.0x1cd8 = 0x48014001 +10009de4 NVC0_COMPUTE.0x1cdc = 0x10009de4 +28004001 NVC0_COMPUTE.0x1ce0 = 0x28004001 +fc21dc43 NVC0_COMPUTE.0x1ce4 = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0x1ce8 = 0x198e0000 +200081e7 NVC0_COMPUTE.0x1cec = 0x200081e7 +40000001 NVC0_COMPUTE.0x1cf0 = 0x40000001 +e0002003 NVC0_COMPUTE.0x1cf4 = 0xe0002003 +48014000 NVC0_COMPUTE.0x1cf8 = 0x48014000 +800121e4 NVC0_COMPUTE.0x1cfc = 0x800121e4 +28004000 NVC0_COMPUTE.0x1d00 = 0x28004000 +f3f0a043 NVC0_COMPUTE.0x1d04 = 0xf3f0a043 +48004000 NVC0_COMPUTE.0x1d08 = 0x48004000 +7800e003 NVC0_COMPUTE.0x1d0c = 0x7800e003 +5800c000 NVC0_COMPUTE.0x1d10 = 0x5800c000 +10012003 NVC0_COMPUTE.0x1d14 = 0x10012003 +2009c000 NVC0_COMPUTE.0x1d18 = 0x2009c000 +a00021e4 NVC0_COMPUTE.0x1d1c = 0xa00021e4 +28004000 NVC0_COMPUTE.0x1d20 = 0x28004000 +0c216043 NVC0_COMPUTE.0x1d24 = 0xc216043 +40000000 NVC0_COMPUTE.0x1d28 = 0x40000000 +90516043 NVC0_COMPUTE.0x1d2c = 0x90516043 +48004000 NVC0_COMPUTE.0x1d30 = 0x48004000 +00402085 NVC0_COMPUTE.0x1d34 = 0x402085 +94000000 NVC0_COMPUTE.0x1d38 = 0x94000000 +00001de7 NVC0_COMPUTE.0x1d3c = 0x1de7 +80000000 NVC0_COMPUTE.0x1d40 = 0x80000000 +200446c0 NVC0_COMPUTE.0x1d44 = 0x200446c0 +00000000 NVC0_COMPUTE.0x1d48 = 0 +0800ffd0 NVC0_COMPUTE.0x1d4c = 0x800ffd0 +00000040 NVC0_COMPUTE.0x1d50 = 0x40 +00000000 NVC0_COMPUTE.0x1d54 = 0 +# out of band: 000001f8 08106518 +# out of band: 000001fc 00011a00 +200145a6 NVC0_COMPUTE.0x1d58 = 0x200145a6 +00000001 NVC0_COMPUTE.0x1d5c = 0x1 +200446c0 NVC0_COMPUTE.0x1d60 = 0x200446c0 +00000000 NVC0_COMPUTE.0x1d64 = 0 +0800ffd0 NVC0_COMPUTE.0x1d68 = 0x800ffd0 +00000041 NVC0_COMPUTE.0x1d6c = 0x41 +00000000 NVC0_COMPUTE.0x1d70 = 0 +# out of band: 00000200 08106630 +# out of band: 00000204 00001e00 +200348e0 NVC0_COMPUTE.0x1d74 = 0x200348e0 +00010000 NVC0_COMPUTE.0x1d78 = 0x10000 +00000001 NVC0_COMPUTE.0x1d7c = 0x1 +00004300 NVC0_COMPUTE.0x1d80 = 0x4300 +200148e3 NVC0_COMPUTE.0x1d84 = 0x200148e3 +00000000 NVC0_COMPUTE.0x1d88 = 0 +603848e4 NVC0_COMPUTE.0x1d8c = 0x603848e4 +00005de4 NVC0_COMPUTE.0x1d90 = 0x5de4 +28004404 NVC0_COMPUTE.0x1d94 = 0x28004404 +94001c04 NVC0_COMPUTE.0x1d98 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x1d9c = 0x2c000000 +84009c04 NVC0_COMPUTE.0x1da0 = 0x84009c04 +2c000000 NVC0_COMPUTE.0x1da4 = 0x2c000000 +08001cc3 NVC0_COMPUTE.0x1da8 = 0x8001cc3 +40000000 NVC0_COMPUTE.0x1dac = 0x40000000 +d0009de4 NVC0_COMPUTE.0x1db0 = 0xd0009de4 +28004000 NVC0_COMPUTE.0x1db4 = 0x28004000 +c00fde03 NVC0_COMPUTE.0x1db8 = 0xc00fde03 +48014000 NVC0_COMPUTE.0x1dbc = 0x48014000 +fc21dc43 NVC0_COMPUTE.0x1dc0 = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0x1dc4 = 0x198e0000 +e00001e7 NVC0_COMPUTE.0x1dc8 = 0xe00001e7 +40000000 NVC0_COMPUTE.0x1dcc = 0x40000000 +80011de4 NVC0_COMPUTE.0x1dd0 = 0x80011de4 +28004000 NVC0_COMPUTE.0x1dd4 = 0x28004000 +7c009c03 NVC0_COMPUTE.0x1dd8 = 0x7c009c03 +5800c000 NVC0_COMPUTE.0x1ddc = 0x5800c000 +08011c03 NVC0_COMPUTE.0x1de0 = 0x8011c03 +2009c000 NVC0_COMPUTE.0x1de4 = 0x2009c000 +a1101c04 NVC0_COMPUTE.0x1de8 = 0xa1101c04 +1c004000 NVC0_COMPUTE.0x1dec = 0x1c004000 +90215c43 NVC0_COMPUTE.0x1df0 = 0x90215c43 +48004000 NVC0_COMPUTE.0x1df4 = 0x48004000 +00401c45 NVC0_COMPUTE.0x1df8 = 0x401c45 +94000000 NVC0_COMPUTE.0x1dfc = 0x94000000 +80001de7 NVC0_COMPUTE.0x1e00 = 0x80001de7 +40000001 NVC0_COMPUTE.0x1e04 = 0x40000001 +000fde03 NVC0_COMPUTE.0x1e08 = 0xfde03 +48014001 NVC0_COMPUTE.0x1e0c = 0x48014001 +10009de4 NVC0_COMPUTE.0x1e10 = 0x10009de4 +28004001 NVC0_COMPUTE.0x1e14 = 0x28004001 +fc21dc43 NVC0_COMPUTE.0x1e18 = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0x1e1c = 0x198e0000 +000081e7 NVC0_COMPUTE.0x1e20 = 0x81e7 +40000001 NVC0_COMPUTE.0x1e24 = 0x40000001 +e0002003 NVC0_COMPUTE.0x1e28 = 0xe0002003 +48014000 NVC0_COMPUTE.0x1e2c = 0x48014000 +f3f0a043 NVC0_COMPUTE.0x1e30 = 0xf3f0a043 +48004000 NVC0_COMPUTE.0x1e34 = 0x48004000 +00002003 NVC0_COMPUTE.0x1e38 = 0x2003 +48010000 NVC0_COMPUTE.0x1e3c = 0x48010000 +0820a043 NVC0_COMPUTE.0x1e40 = 0x820a043 +48000000 NVC0_COMPUTE.0x1e44 = 0x48000000 +80012003 NVC0_COMPUTE.0x1e48 = 0x80012003 +48014000 NVC0_COMPUTE.0x1e4c = 0x48014000 +a1102004 NVC0_COMPUTE.0x1e50 = 0xa1102004 +1c004000 NVC0_COMPUTE.0x1e54 = 0x1c004000 +90216043 NVC0_COMPUTE.0x1e58 = 0x90216043 +48004000 NVC0_COMPUTE.0x1e5c = 0x48004000 +00402045 NVC0_COMPUTE.0x1e60 = 0x402045 +94000000 NVC0_COMPUTE.0x1e64 = 0x94000000 +00001de7 NVC0_COMPUTE.0x1e68 = 0x1de7 +80000000 NVC0_COMPUTE.0x1e6c = 0x80000000 +200446c0 NVC0_COMPUTE.0x1e70 = 0x200446c0 +00000000 NVC0_COMPUTE.0x1e74 = 0 +0800ffd0 NVC0_COMPUTE.0x1e78 = 0x800ffd0 +00000042 NVC0_COMPUTE.0x1e7c = 0x42 +00000000 NVC0_COMPUTE.0x1e80 = 0 +# out of band: 00000208 0810664c +# out of band: 0000020c 00011200 +200145a6 NVC0_COMPUTE.0x1e84 = 0x200145a6 +00000001 NVC0_COMPUTE.0x1e88 = 0x1 +200446c0 NVC0_COMPUTE.0x1e8c = 0x200446c0 +00000000 NVC0_COMPUTE.0x1e90 = 0 +0800ffd0 NVC0_COMPUTE.0x1e94 = 0x800ffd0 +00000043 NVC0_COMPUTE.0x1e98 = 0x43 +00000000 NVC0_COMPUTE.0x1e9c = 0 +# out of band: 00000210 0810675c +# out of band: 00000214 00001e00 +200348e0 NVC0_COMPUTE.0x1ea0 = 0x200348e0 +00010000 NVC0_COMPUTE.0x1ea4 = 0x10000 +00000001 NVC0_COMPUTE.0x1ea8 = 0x1 +00004200 NVC0_COMPUTE.0x1eac = 0x4200 +200148e3 NVC0_COMPUTE.0x1eb0 = 0x200148e3 +00000000 NVC0_COMPUTE.0x1eb4 = 0 +603048e4 NVC0_COMPUTE.0x1eb8 = 0x603048e4 +00005de4 NVC0_COMPUTE.0x1ebc = 0x5de4 +28004404 NVC0_COMPUTE.0x1ec0 = 0x28004404 +94001c04 NVC0_COMPUTE.0x1ec4 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x1ec8 = 0x2c000000 +84009c04 NVC0_COMPUTE.0x1ecc = 0x84009c04 +2c000000 NVC0_COMPUTE.0x1ed0 = 0x2c000000 +08001cc3 NVC0_COMPUTE.0x1ed4 = 0x8001cc3 +40000000 NVC0_COMPUTE.0x1ed8 = 0x40000000 +d0009de4 NVC0_COMPUTE.0x1edc = 0xd0009de4 +28004000 NVC0_COMPUTE.0x1ee0 = 0x28004000 +c00fde03 NVC0_COMPUTE.0x1ee4 = 0xc00fde03 +48014000 NVC0_COMPUTE.0x1ee8 = 0x48014000 +fc21dc43 NVC0_COMPUTE.0x1eec = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0x1ef0 = 0x198e0000 +a00001e7 NVC0_COMPUTE.0x1ef4 = 0xa00001e7 +40000000 NVC0_COMPUTE.0x1ef8 = 0x40000000 +80009c03 NVC0_COMPUTE.0x1efc = 0x80009c03 +48014000 NVC0_COMPUTE.0x1f00 = 0x48014000 +a1001c04 NVC0_COMPUTE.0x1f04 = 0xa1001c04 +1c004000 NVC0_COMPUTE.0x1f08 = 0x1c004000 +93f0dc43 NVC0_COMPUTE.0x1f0c = 0x93f0dc43 +48004000 NVC0_COMPUTE.0x1f10 = 0x48004000 +00201c05 NVC0_COMPUTE.0x1f14 = 0x201c05 +94000000 NVC0_COMPUTE.0x1f18 = 0x94000000 +40001de7 NVC0_COMPUTE.0x1f1c = 0x40001de7 +40000001 NVC0_COMPUTE.0x1f20 = 0x40000001 +000fde03 NVC0_COMPUTE.0x1f24 = 0xfde03 +48014001 NVC0_COMPUTE.0x1f28 = 0x48014001 +10009de4 NVC0_COMPUTE.0x1f2c = 0x10009de4 +28004001 NVC0_COMPUTE.0x1f30 = 0x28004001 +fc21dc43 NVC0_COMPUTE.0x1f34 = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0x1f38 = 0x198e0000 +c00081e7 NVC0_COMPUTE.0x1f3c = 0xc00081e7 +40000000 NVC0_COMPUTE.0x1f40 = 0x40000000 +e0002003 NVC0_COMPUTE.0x1f44 = 0xe0002003 +48014000 NVC0_COMPUTE.0x1f48 = 0x48014000 +f3f0a043 NVC0_COMPUTE.0x1f4c = 0xf3f0a043 +48004000 NVC0_COMPUTE.0x1f50 = 0x48004000 +80012003 NVC0_COMPUTE.0x1f54 = 0x80012003 +48014000 NVC0_COMPUTE.0x1f58 = 0x48014000 +a1002004 NVC0_COMPUTE.0x1f5c = 0xa1002004 +1c004000 NVC0_COMPUTE.0x1f60 = 0x1c004000 +90216043 NVC0_COMPUTE.0x1f64 = 0x90216043 +48004000 NVC0_COMPUTE.0x1f68 = 0x48004000 +00402005 NVC0_COMPUTE.0x1f6c = 0x402005 +94000000 NVC0_COMPUTE.0x1f70 = 0x94000000 +00001de7 NVC0_COMPUTE.0x1f74 = 0x1de7 +80000000 NVC0_COMPUTE.0x1f78 = 0x80000000 +200446c0 NVC0_COMPUTE.0x1f7c = 0x200446c0 +00000000 NVC0_COMPUTE.0x1f80 = 0 +0800ffd0 NVC0_COMPUTE.0x1f84 = 0x800ffd0 +00000044 NVC0_COMPUTE.0x1f88 = 0x44 +00000000 NVC0_COMPUTE.0x1f8c = 0 +# out of band: 00000218 08106778 +# out of band: 0000021c 0000f200 +200145a6 NVC0_COMPUTE.0x1f90 = 0x200145a6 +00000001 NVC0_COMPUTE.0x1f94 = 0x1 +200446c0 NVC0_COMPUTE.0x1f98 = 0x200446c0 +00000000 NVC0_COMPUTE.0x1f9c = 0 +0800ffd0 NVC0_COMPUTE.0x1fa0 = 0x800ffd0 +00000045 NVC0_COMPUTE.0x1fa4 = 0x45 +00000000 NVC0_COMPUTE.0x1fa8 = 0 +# out of band: 00000220 08106868 +# out of band: 00000224 00001e00 +200348e0 NVC0_COMPUTE.0x1fac = 0x200348e0 +00010000 NVC0_COMPUTE.0x1fb0 = 0x10000 +00000001 NVC0_COMPUTE.0x1fb4 = 0x1 +00004100 NVC0_COMPUTE.0x1fb8 = 0x4100 +200148e3 NVC0_COMPUTE.0x1fbc = 0x200148e3 +00000000 NVC0_COMPUTE.0x1fc0 = 0 +601e48e4 NVC0_COMPUTE.0x1fc4 = 0x601e48e4 +00005de4 NVC0_COMPUTE.0x1fc8 = 0x5de4 +28004404 NVC0_COMPUTE.0x1fcc = 0x28004404 +94001c04 NVC0_COMPUTE.0x1fd0 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x1fd4 = 0x2c000000 +84009c04 NVC0_COMPUTE.0x1fd8 = 0x84009c04 +2c000000 NVC0_COMPUTE.0x1fdc = 0x2c000000 +08001cc3 NVC0_COMPUTE.0x1fe0 = 0x8001cc3 +40000000 NVC0_COMPUTE.0x1fe4 = 0x40000000 +d0009de4 NVC0_COMPUTE.0x1fe8 = 0xd0009de4 +28004000 NVC0_COMPUTE.0x1fec = 0x28004000 +c00fde03 NVC0_COMPUTE.0x1ff0 = 0xc00fde03 +48014000 NVC0_COMPUTE.0x1ff4 = 0x48014000 +fc21dc43 NVC0_COMPUTE.0x1ff8 = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0x1ffc = 0x198e0000 +c00081e7 NVC0_COMPUTE.0x2000 = 0xc00081e7 +40000000 NVC0_COMPUTE.0x2004 = 0x40000000 +800121e4 NVC0_COMPUTE.0x2008 = 0x800121e4 +28004000 NVC0_COMPUTE.0x200c = 0x28004000 +7800a003 NVC0_COMPUTE.0x2010 = 0x7800a003 +5800c000 NVC0_COMPUTE.0x2014 = 0x5800c000 +10012003 NVC0_COMPUTE.0x2018 = 0x10012003 +2009c000 NVC0_COMPUTE.0x201c = 0x2009c000 +a00021e4 NVC0_COMPUTE.0x2020 = 0xa00021e4 +28004000 NVC0_COMPUTE.0x2024 = 0x28004000 +90216043 NVC0_COMPUTE.0x2028 = 0x90216043 +48004000 NVC0_COMPUTE.0x202c = 0x48004000 +00402085 NVC0_COMPUTE.0x2030 = 0x402085 +94000000 NVC0_COMPUTE.0x2034 = 0x94000000 +00001de7 NVC0_COMPUTE.0x2038 = 0x1de7 +80000000 NVC0_COMPUTE.0x203c = 0x80000000 +200446c0 NVC0_COMPUTE.0x2040 = 0x200446c0 +00000000 NVC0_COMPUTE.0x2044 = 0 +0800ffd0 NVC0_COMPUTE.0x2048 = 0x800ffd0 +00000046 NVC0_COMPUTE.0x204c = 0x46 +00000000 NVC0_COMPUTE.0x2050 = 0 +# out of band: 00000228 08106884 +# out of band: 0000022c 0000aa00 +200145a6 NVC0_COMPUTE.0x2054 = 0x200145a6 +00000001 NVC0_COMPUTE.0x2058 = 0x1 +200446c0 NVC0_COMPUTE.0x205c = 0x200446c0 +00000000 NVC0_COMPUTE.0x2060 = 0 +0800ffd0 NVC0_COMPUTE.0x2064 = 0x800ffd0 +00000047 NVC0_COMPUTE.0x2068 = 0x47 +00000000 NVC0_COMPUTE.0x206c = 0 +# out of band: 00000230 0810692c +# out of band: 00000234 00001e00 +200348e0 NVC0_COMPUTE.0x2070 = 0x200348e0 +00010000 NVC0_COMPUTE.0x2074 = 0x10000 +00000001 NVC0_COMPUTE.0x2078 = 0x1 +00004000 NVC0_COMPUTE.0x207c = 0x4000 +200148e3 NVC0_COMPUTE.0x2080 = 0x200148e3 +00000000 NVC0_COMPUTE.0x2084 = 0 +601e48e4 NVC0_COMPUTE.0x2088 = 0x601e48e4 +00005de4 NVC0_COMPUTE.0x208c = 0x5de4 +28004404 NVC0_COMPUTE.0x2090 = 0x28004404 +94001c04 NVC0_COMPUTE.0x2094 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x2098 = 0x2c000000 +84009c04 NVC0_COMPUTE.0x209c = 0x84009c04 +2c000000 NVC0_COMPUTE.0x20a0 = 0x2c000000 +08001cc3 NVC0_COMPUTE.0x20a4 = 0x8001cc3 +40000000 NVC0_COMPUTE.0x20a8 = 0x40000000 +d0009de4 NVC0_COMPUTE.0x20ac = 0xd0009de4 +28004000 NVC0_COMPUTE.0x20b0 = 0x28004000 +c00fde03 NVC0_COMPUTE.0x20b4 = 0xc00fde03 +48014000 NVC0_COMPUTE.0x20b8 = 0x48014000 +fc21dc43 NVC0_COMPUTE.0x20bc = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0x20c0 = 0x198e0000 +c00081e7 NVC0_COMPUTE.0x20c4 = 0xc00081e7 +40000000 NVC0_COMPUTE.0x20c8 = 0x40000000 +800121e4 NVC0_COMPUTE.0x20cc = 0x800121e4 +28004000 NVC0_COMPUTE.0x20d0 = 0x28004000 +7c00a003 NVC0_COMPUTE.0x20d4 = 0x7c00a003 +5800c000 NVC0_COMPUTE.0x20d8 = 0x5800c000 +08012003 NVC0_COMPUTE.0x20dc = 0x8012003 +2009c000 NVC0_COMPUTE.0x20e0 = 0x2009c000 +a1102004 NVC0_COMPUTE.0x20e4 = 0xa1102004 +1c004000 NVC0_COMPUTE.0x20e8 = 0x1c004000 +90216043 NVC0_COMPUTE.0x20ec = 0x90216043 +48004000 NVC0_COMPUTE.0x20f0 = 0x48004000 +00402045 NVC0_COMPUTE.0x20f4 = 0x402045 +94000000 NVC0_COMPUTE.0x20f8 = 0x94000000 +00001de7 NVC0_COMPUTE.0x20fc = 0x1de7 +80000000 NVC0_COMPUTE.0x2100 = 0x80000000 +200446c0 NVC0_COMPUTE.0x2104 = 0x200446c0 +00000000 NVC0_COMPUTE.0x2108 = 0 +0800ffd0 NVC0_COMPUTE.0x210c = 0x800ffd0 +00000048 NVC0_COMPUTE.0x2110 = 0x48 +00000000 NVC0_COMPUTE.0x2114 = 0 +# out of band: 00000238 08106948 +# out of band: 0000023c 0000aa00 +200145a6 NVC0_COMPUTE.0x2118 = 0x200145a6 +00000001 NVC0_COMPUTE.0x211c = 0x1 +200446c0 NVC0_COMPUTE.0x2120 = 0x200446c0 +00000000 NVC0_COMPUTE.0x2124 = 0 +0800ffd0 NVC0_COMPUTE.0x2128 = 0x800ffd0 +00000049 NVC0_COMPUTE.0x212c = 0x49 +00000000 NVC0_COMPUTE.0x2130 = 0 +# out of band: 00000240 081069f0 +# out of band: 00000244 00001e00 +200348e0 NVC0_COMPUTE.0x2134 = 0x200348e0 +00010000 NVC0_COMPUTE.0x2138 = 0x10000 +00000001 NVC0_COMPUTE.0x213c = 0x1 +00003f00 NVC0_COMPUTE.0x2140 = 0x3f00 +200148e3 NVC0_COMPUTE.0x2144 = 0x200148e3 +00000000 NVC0_COMPUTE.0x2148 = 0 +601a48e4 NVC0_COMPUTE.0x214c = 0x601a48e4 +00005de4 NVC0_COMPUTE.0x2150 = 0x5de4 +28004404 NVC0_COMPUTE.0x2154 = 0x28004404 +94001c04 NVC0_COMPUTE.0x2158 = 0x94001c04 +2c000000 NVC0_COMPUTE.0x215c = 0x2c000000 +84009c04 NVC0_COMPUTE.0x2160 = 0x84009c04 +2c000000 NVC0_COMPUTE.0x2164 = 0x2c000000 +08001cc3 NVC0_COMPUTE.0x2168 = 0x8001cc3 +40000000 NVC0_COMPUTE.0x216c = 0x40000000 +d0009de4 NVC0_COMPUTE.0x2170 = 0xd0009de4 +28004000 NVC0_COMPUTE.0x2174 = 0x28004000 +c00fde03 NVC0_COMPUTE.0x2178 = 0xc00fde03 +48014000 NVC0_COMPUTE.0x217c = 0x48014000 +fc21dc43 NVC0_COMPUTE.0x2180 = 0xfc21dc43 +198e0000 NVC0_COMPUTE.0x2184 = 0x198e0000 +800081e7 NVC0_COMPUTE.0x2188 = 0x800081e7 +40000000 NVC0_COMPUTE.0x218c = 0x40000000 +8000a003 NVC0_COMPUTE.0x2190 = 0x8000a003 +48014000 NVC0_COMPUTE.0x2194 = 0x48014000 +a1002004 NVC0_COMPUTE.0x2198 = 0xa1002004 +1c004000 NVC0_COMPUTE.0x219c = 0x1c004000 +93f0e043 NVC0_COMPUTE.0x21a0 = 0x93f0e043 +48004000 NVC0_COMPUTE.0x21a4 = 0x48004000 +00202005 NVC0_COMPUTE.0x21a8 = 0x202005 +94000000 NVC0_COMPUTE.0x21ac = 0x94000000 +00001de7 NVC0_COMPUTE.0x21b0 = 0x1de7 +80000000 NVC0_COMPUTE.0x21b4 = 0x80000000 +200446c0 NVC0_COMPUTE.0x21b8 = 0x200446c0 +00000000 NVC0_COMPUTE.0x21bc = 0 +0800ffd0 NVC0_COMPUTE.0x21c0 = 0x800ffd0 +0000004a NVC0_COMPUTE.0x21c4 = 0x4a +00000000 NVC0_COMPUTE.0x21c8 = 0 +# out of band: 00000248 08106a0c +# out of band: 0000024c 00009a00 +200145a6 NVC0_COMPUTE.0x21cc = 0x200145a6 +00000001 NVC0_COMPUTE.0x21d0 = 0x1 +200446c0 NVC0_COMPUTE.0x21d4 = 0x200446c0 +00000000 NVC0_COMPUTE.0x21d8 = 0 +0800ffd0 NVC0_COMPUTE.0x21dc = 0x800ffd0 +0000004b NVC0_COMPUTE.0x21e0 = 0x4b +00000000 NVC0_COMPUTE.0x21e4 = 0 +# out of band: 00000250 08106aa4 +# out of band: 00000254 00001e00 +200348e0 NVC0_COMPUTE.0x21e8 = 0x200348e0 +00010000 NVC0_COMPUTE.0x21ec = 0x10000 +00000001 NVC0_COMPUTE.0x21f0 = 0x1 +00003e00 NVC0_COMPUTE.0x21f4 = 0x3e00 +200148e3 NVC0_COMPUTE.0x21f8 = 0x200148e3 +00000000 NVC0_COMPUTE.0x21fc = 0 +602248e4 NVC0_COMPUTE.0x2200 = 0x602248e4 +00005de4 NVC0_COMPUTE.0x2204 = 0x5de4 +28004404 NVC0_COMPUTE.0x2208 = 0x28004404 +94009c04 NVC0_COMPUTE.0x220c = 0x94009c04 +2c000000 NVC0_COMPUTE.0x2210 = 0x2c000000 +98001c04 NVC0_COMPUTE.0x2214 = 0x98001c04 +2c000000 NVC0_COMPUTE.0x2218 = 0x2c000000 +8000dde4 NVC0_COMPUTE.0x221c = 0x8000dde4 +28004000 NVC0_COMPUTE.0x2220 = 0x28004000 +a0011de4 NVC0_COMPUTE.0x2224 = 0xa0011de4 +28004000 NVC0_COMPUTE.0x2228 = 0x28004000 +50001c03 NVC0_COMPUTE.0x222c = 0x50001c03 +20044000 NVC0_COMPUTE.0x2230 = 0x20044000 +84009c04 NVC0_COMPUTE.0x2234 = 0x84009c04 +2c000000 NVC0_COMPUTE.0x2238 = 0x2c000000 +18001e03 NVC0_COMPUTE.0x223c = 0x18001e03 +6000c000 NVC0_COMPUTE.0x2240 = 0x6000c000 +08001c43 NVC0_COMPUTE.0x2244 = 0x8001c43 +40000000 NVC0_COMPUTE.0x2248 = 0x40000000 +10009c03 NVC0_COMPUTE.0x224c = 0x10009c03 +2007c000 NVC0_COMPUTE.0x2250 = 0x2007c000 +10001c43 NVC0_COMPUTE.0x2254 = 0x10001c43 +5000c000 NVC0_COMPUTE.0x2258 = 0x5000c000 +9000dc43 NVC0_COMPUTE.0x225c = 0x9000dc43 +48004000 NVC0_COMPUTE.0x2260 = 0x48004000 +00211c85 NVC0_COMPUTE.0x2264 = 0x211c85 +94000000 NVC0_COMPUTE.0x2268 = 0x94000000 +00211c85 NVC0_COMPUTE.0x226c = 0x211c85 +94000004 NVC0_COMPUTE.0x2270 = 0x94000004 +00211c85 NVC0_COMPUTE.0x2274 = 0x211c85 +94000008 NVC0_COMPUTE.0x2278 = 0x94000008 +00211c85 NVC0_COMPUTE.0x227c = 0x211c85 +9400000c NVC0_COMPUTE.0x2280 = 0x9400000c +00001de7 NVC0_COMPUTE.0x2284 = 0x1de7 +80000000 NVC0_COMPUTE.0x2288 = 0x80000000 +200446c0 NVC0_COMPUTE.0x228c = 0x200446c0 +00000000 NVC0_COMPUTE.0x2290 = 0 +0800ffd0 NVC0_COMPUTE.0x2294 = 0x800ffd0 +0000004c NVC0_COMPUTE.0x2298 = 0x4c +00000000 NVC0_COMPUTE.0x229c = 0 +# out of band: 00000258 08106ac0 +# out of band: 0000025c 0000ba00 +200145a6 NVC0_COMPUTE.0x22a0 = 0x200145a6 +00000001 NVC0_COMPUTE.0x22a4 = 0x1 +200446c0 NVC0_COMPUTE.0x22a8 = 0x200446c0 +00000000 NVC0_COMPUTE.0x22ac = 0 +0800ffd0 NVC0_COMPUTE.0x22b0 = 0x800ffd0 +0000004d NVC0_COMPUTE.0x22b4 = 0x4d +00000000 NVC0_COMPUTE.0x22b8 = 0 +# out of band: 00000260 08106b78 +# out of band: 00000264 00001e00 +200348e0 NVC0_COMPUTE.0x22bc = 0x200348e0 +00010000 NVC0_COMPUTE.0x22c0 = 0x10000 +00000001 NVC0_COMPUTE.0x22c4 = 0x1 +0000bb00 NVC0_COMPUTE.0x22c8 = 0xbb00 +200148e3 NVC0_COMPUTE.0x22cc = 0x200148e3 +00000000 NVC0_COMPUTE.0x22d0 = 0 +606c48e4 NVC0_COMPUTE.0x22d4 = 0x606c48e4 +10401f85 NVC0_COMPUTE.0x22d8 = 0x10401f85 +84000000 NVC0_COMPUTE.0x22dc = 0x84000000 +20019c03 NVC0_COMPUTE.0x22e0 = 0x20019c03 +6000c000 NVC0_COMPUTE.0x22e4 = 0x6000c000 +6001dc03 NVC0_COMPUTE.0x22e8 = 0x6001dc03 +5800c000 NVC0_COMPUTE.0x22ec = 0x5800c000 +00601f45 NVC0_COMPUTE.0x22f0 = 0x601f45 +84000000 NVC0_COMPUTE.0x22f4 = 0x84000000 +0c01dc23 NVC0_COMPUTE.0x22f8 = 0xc01dc23 +190ec16b NVC0_COMPUTE.0x22fc = 0x190ec16b +400001e7 NVC0_COMPUTE.0x2300 = 0x400001e7 +40000000 NVC0_COMPUTE.0x2304 = 0x40000000 +fc011de2 NVC0_COMPUTE.0x2308 = 0xfc011de2 +1bffffff NVC0_COMPUTE.0x230c = 0x1bffffff +a0001de7 NVC0_COMPUTE.0x2310 = 0xa0001de7 +40000005 NVC0_COMPUTE.0x2314 = 0x40000005 +0040df85 NVC0_COMPUTE.0x2318 = 0x40df85 +84000000 NVC0_COMPUTE.0x231c = 0x84000000 +00401f85 NVC0_COMPUTE.0x2320 = 0x401f85 +84000000 NVC0_COMPUTE.0x2324 = 0x84000000 +40000007 NVC0_COMPUTE.0x2328 = 0x40000007 +68000005 NVC0_COMPUTE.0x232c = 0x68000005 +08011de2 NVC0_COMPUTE.0x2330 = 0x8011de2 +18000000 NVC0_COMPUTE.0x2334 = 0x18000000 +1430dc03 NVC0_COMPUTE.0x2338 = 0x1430dc03 +6000c000 NVC0_COMPUTE.0x233c = 0x6000c000 +6c30dc03 NVC0_COMPUTE.0x2340 = 0x6c30dc03 +5800c000 NVC0_COMPUTE.0x2344 = 0x5800c000 +0c40dc03 NVC0_COMPUTE.0x2348 = 0xc40dc03 +60000000 NVC0_COMPUTE.0x234c = 0x60000000 +28011c03 NVC0_COMPUTE.0x2350 = 0x28011c03 +6000c000 NVC0_COMPUTE.0x2354 = 0x6000c000 +fc301c03 NVC0_COMPUTE.0x2358 = 0xfc301c03 +4800ffff NVC0_COMPUTE.0x235c = 0x4800ffff +68411c03 NVC0_COMPUTE.0x2360 = 0x68411c03 +5800c000 NVC0_COMPUTE.0x2364 = 0x5800c000 +fc00dde4 NVC0_COMPUTE.0x2368 = 0xfc00dde4 +28000000 NVC0_COMPUTE.0x236c = 0x28000000 +10001c03 NVC0_COMPUTE.0x2370 = 0x10001c03 +60000000 NVC0_COMPUTE.0x2374 = 0x60000000 +10611f85 NVC0_COMPUTE.0x2378 = 0x10611f85 +84000000 NVC0_COMPUTE.0x237c = 0x84000000 +10015c03 NVC0_COMPUTE.CB_SIZE = 0x10015c03 +68000000 NVC0_COMPUTE.CB_ADDRESS_HIGH = 0x68000000 +fc51dc03 NVC0_COMPUTE.CB_ADDRESS_LOW = 0xfc51dc03 +190e0000 NVC0_COMPUTE.CB_POS = 0x190e0000 +600001e7 NVC0_COMPUTE.CB_DATA[0] = 0x600001e7 +40000000 NVC0_COMPUTE.CB_DATA[0x1] = 0x40000000 +03ffdf85 NVC0_COMPUTE.CB_DATA[0x2] = 0x3ffdf85 +94000000 NVC0_COMPUTE.CB_DATA[0x3] = 0x94000000 +fc011de4 NVC0_COMPUTE.CB_DATA[0x4] = 0xfc011de4 +28000000 NVC0_COMPUTE.CB_DATA[0x5] = 0x28000000 +00001de7 NVC0_COMPUTE.CB_DATA[0x6] = 0x1de7 +a8000000 NVC0_COMPUTE.CB_DATA[0x7] = 0xa8000000 +10615c03 NVC0_COMPUTE.CB_DATA[0x8] = 0x10615c03 +4801c000 NVC0_COMPUTE.CB_DATA[0x9] = 0x4801c000 +00000007 NVC0_COMPUTE.CB_DATA[0xa] = 0x7 +60000002 NVC0_COMPUTE.CB_DATA[0xb] = 0x60000002 +00521c02 NVC0_COMPUTE.CB_DATA[0xc] = 0x521c02 +3bfc0000 NVC0_COMPUTE.CB_DATA[0xd] = 0x3bfc0000 +1ff15c43 NVC0_COMPUTE.CB_DATA[0xe] = 0x1ff15c43 +48000000 NVC0_COMPUTE.CB_DATA[0xf] = 0x48000000 +0081dc03 NVC0_COMPUTE.0x23d0 = 0x81dc03 +190e4000 NVC0_COMPUTE.0x23d4 = 0x190e4000 +fc53dc03 NVC0_COMPUTE.0x23d8 = 0xfc53dc03 +190e0000 NVC0_COMPUTE.0x23dc = 0x190e0000 +10015c43 NVC0_COMPUTE.0x23e0 = 0x10015c43 +68000000 NVC0_COMPUTE.0x23e4 = 0x68000000 +0401dc04 NVC0_COMPUTE.0x23e8 = 0x401dc04 +0c0e0000 NVC0_COMPUTE.0x23ec = 0xc0e0000 +600001e7 NVC0_COMPUTE.0x23f0 = 0x600001e7 +40000000 NVC0_COMPUTE.0x23f4 = 0x40000000 +10611d25 NVC0_COMPUTE.0x23f8 = 0x10611d25 +540a4000 NVC0_COMPUTE.0x23fc = 0x540a4000 +10601ca5 NVC0_COMPUTE.0x2400 = 0x10601ca5 +9c000000 NVC0_COMPUTE.0x2404 = 0x9c000000 +a0001de7 NVC0_COMPUTE.0x2408 = 0xa0001de7 +40000000 NVC0_COMPUTE.0x240c = 0x40000000 +10621c85 NVC0_COMPUTE.0x2410 = 0x10621c85 +a0000000 NVC0_COMPUTE.0x2414 = 0xa0000000 +1083c003 NVC0_COMPUTE.0x2418 = 0x1083c003 +190e0000 NVC0_COMPUTE.0x241c = 0x190e0000 +20524004 NVC0_COMPUTE.0x2420 = 0x20524004 +20020000 NVC0_COMPUTE.0x2424 = 0x20020000 +10624085 NVC0_COMPUTE.0x2428 = 0x10624085 +e8000000 NVC0_COMPUTE.0x242c = 0xe8000000 +600021e7 NVC0_COMPUTE.0x2430 = 0x600021e7 +4003ffff NVC0_COMPUTE.0x2434 = 0x4003ffff +1081dc13 NVC0_COMPUTE.0x2438 = 0x1081dc13 +1a8e0000 NVC0_COMPUTE.0x243c = 0x1a8e0000 +400001e7 NVC0_COMPUTE.0x2440 = 0x400001e7 +40000000 NVC0_COMPUTE.0x2444 = 0x40000000 +04011de2 NVC0_COMPUTE.0x2448 = 0x4011de2 +18000000 NVC0_COMPUTE.0x244c = 0x18000000 +00001de7 NVC0_COMPUTE.0x2450 = 0x1de7 +a8000000 NVC0_COMPUTE.0x2454 = 0xa8000000 +0430dc03 NVC0_COMPUTE.0x2458 = 0x430dc03 +4800c000 NVC0_COMPUTE.0x245c = 0x4800c000 +4031dc23 NVC0_COMPUTE.0x2460 = 0x4031dc23 +1a8ec30d NVC0_COMPUTE.0x2464 = 0x1a8ec30d +200001e7 NVC0_COMPUTE.0x2468 = 0x200001e7 +4003fffc NVC0_COMPUTE.0x246c = 0x4003fffc +fc011de4 NVC0_COMPUTE.0x2470 = 0xfc011de4 +28000000 NVC0_COMPUTE.0x2474 = 0x28000000 +00001de7 NVC0_COMPUTE.0x2478 = 0x1de7 +a8000000 NVC0_COMPUTE.0x247c = 0xa8000000 +00001de7 NVC0_COMPUTE.0x2480 = 0x1de7 +90000000 NVC0_COMPUTE.0x2484 = 0x90000000 +200446c0 NVC0_COMPUTE.0x2488 = 0x200446c0 +00000000 NVC0_COMPUTE.0x248c = 0 +0800ffd0 NVC0_COMPUTE.0x2490 = 0x800ffd0 +0000004e NVC0_COMPUTE.0x2494 = 0x4e +00000000 NVC0_COMPUTE.0x2498 = 0 +# out of band: 00000268 08106b94 +# out of band: 0000026c 0001e200 +200145a6 NVC0_COMPUTE.0x249c = 0x200145a6 +00000001 NVC0_COMPUTE.0x24a0 = 0x1 +200446c0 NVC0_COMPUTE.0x24a4 = 0x200446c0 +00000000 NVC0_COMPUTE.0x24a8 = 0 +0800ffd0 NVC0_COMPUTE.0x24ac = 0x800ffd0 +0000004f NVC0_COMPUTE.0x24b0 = 0x4f +00000000 NVC0_COMPUTE.0x24b4 = 0 +# out of band: 00000270 08106d74 +# out of band: 00000274 00001e00 +200348e0 NVC0_COMPUTE.0x24b8 = 0x200348e0 +00010000 NVC0_COMPUTE.0x24bc = 0x10000 +00000001 NVC0_COMPUTE.0x24c0 = 0x1 +0000ba00 NVC0_COMPUTE.0x24c4 = 0xba00 +200148e3 NVC0_COMPUTE.0x24c8 = 0x200148e3 +00000000 NVC0_COMPUTE.0x24cc = 0 +601e48e4 NVC0_COMPUTE.0x24d0 = 0x601e48e4 +20105d03 NVC0_COMPUTE.0x24d4 = 0x20105d03 +4800c000 NVC0_COMPUTE.0x24d8 = 0x4800c000 +14001de4 NVC0_COMPUTE.0x24dc = 0x14001de4 +28000000 NVC0_COMPUTE.0x24e0 = 0x28000000 +00109c85 NVC0_COMPUTE.0x24e4 = 0x109c85 +c8000000 NVC0_COMPUTE.0x24e8 = 0xc8000000 +10101c85 NVC0_COMPUTE.0x24ec = 0x10101c85 +c8000000 NVC0_COMPUTE.0x24f0 = 0xc8000000 +10009de4 NVC0_COMPUTE.0x24f4 = 0x10009de4 +28000000 NVC0_COMPUTE.0x24f8 = 0x28000000 +00010007 NVC0_COMPUTE.0x24fc = 0x10007 +100001c8 NVC0_COMPUTE.0x2500 = 0x100001c8 +10101e85 NVC0_COMPUTE.0x2504 = 0x10101e85 +c0000000 NVC0_COMPUTE.0x2508 = 0xc0000000 +08011de4 NVC0_COMPUTE.0x250c = 0x8011de4 +28000000 NVC0_COMPUTE.0x2510 = 0x28000000 +00109e85 NVC0_COMPUTE.0x2514 = 0x109e85 +c0000000 NVC0_COMPUTE.0x2518 = 0xc0000000 +00015de4 NVC0_COMPUTE.0x251c = 0x15de4 +28000000 NVC0_COMPUTE.0x2520 = 0x28000000 +00010007 NVC0_COMPUTE.0x2524 = 0x10007 +100001d0 NVC0_COMPUTE.0x2528 = 0x100001d0 +fc011de4 NVC0_COMPUTE.0x252c = 0xfc011de4 +28000000 NVC0_COMPUTE.0x2530 = 0x28000000 +00010007 NVC0_COMPUTE.0x2534 = 0x10007 +100001d4 NVC0_COMPUTE.0x2538 = 0x100001d4 +20105c03 NVC0_COMPUTE.0x253c = 0x20105c03 +4800c000 NVC0_COMPUTE.0x2540 = 0x4800c000 +00001de7 NVC0_COMPUTE.0x2544 = 0x1de7 +90000000 NVC0_COMPUTE.0x2548 = 0x90000000 +200446c0 NVC0_COMPUTE.0x254c = 0x200446c0 +00000000 NVC0_COMPUTE.0x2550 = 0 +0800ffd0 NVC0_COMPUTE.0x2554 = 0x800ffd0 +00000050 NVC0_COMPUTE.0x2558 = 0x50 +00000000 NVC0_COMPUTE.0x255c = 0 +# out of band: 00000278 08106d90 +# out of band: 0000027c 0000aa00 +200145a6 NVC0_COMPUTE.0x2560 = 0x200145a6 +00000001 NVC0_COMPUTE.0x2564 = 0x1 +200446c0 NVC0_COMPUTE.0x2568 = 0x200446c0 +00000000 NVC0_COMPUTE.0x256c = 0 +0800ffd0 NVC0_COMPUTE.0x2570 = 0x800ffd0 +00000051 NVC0_COMPUTE.0x2574 = 0x51 +00000000 NVC0_COMPUTE.0x2578 = 0 +# out of band: 00000280 08106e38 +# out of band: 00000284 00001e00 +200348e0 NVC0_COMPUTE.0x257c = 0x200348e0 +00010000 NVC0_COMPUTE.0x2580 = 0x10000 +00000001 NVC0_COMPUTE.0x2584 = 0x1 +00008500 NVC0_COMPUTE.0x2588 = 0x8500 +200148e3 NVC0_COMPUTE.0x258c = 0x200148e3 +00000000 NVC0_COMPUTE.0x2590 = 0 +67ff48e4 NVC0_COMPUTE.0x2594 = 0x67ff48e4 +0400dde4 NVC0_COMPUTE.0x2598 = 0x400dde4 +28000000 NVC0_COMPUTE.0x259c = 0x28000000 +00105d03 NVC0_COMPUTE.0x25a0 = 0x105d03 +4800c005 NVC0_COMPUTE.0x25a4 = 0x4800c005 +c0001de4 NVC0_COMPUTE.0x25a8 = 0xc0001de4 +28004405 NVC0_COMPUTE.0x25ac = 0x28004405 +4041dc03 NVC0_COMPUTE.0x25b0 = 0x4041dc03 +4801c000 NVC0_COMPUTE.0x25b4 = 0x4801c000 +c0105c03 NVC0_COMPUTE.0x25b8 = 0xc0105c03 +6800ffff NVC0_COMPUTE.0x25bc = 0x6800ffff +04001c03 NVC0_COMPUTE.0x25c0 = 0x4001c03 +4800c000 NVC0_COMPUTE.0x25c4 = 0x4800c000 +fc529c43 NVC0_COMPUTE.0x25c8 = 0xfc529c43 +48000000 NVC0_COMPUTE.0x25cc = 0x48000000 +c0109ca5 NVC0_COMPUTE.0x25d0 = 0xc0109ca5 +c8000002 NVC0_COMPUTE.0x25d4 = 0xc8000002 +fc009de4 NVC0_COMPUTE.0x25d8 = 0xfc009de4 +28000000 NVC0_COMPUTE.0x25dc = 0x28000000 +0820de03 NVC0_COMPUTE.0x25e0 = 0x820de03 +6000c000 NVC0_COMPUTE.0x25e4 = 0x6000c000 +7c221c23 NVC0_COMPUTE.0x25e8 = 0x7c221c23 +7000c004 NVC0_COMPUTE.0x25ec = 0x7000c004 +00319c86 NVC0_COMPUTE.0x25f0 = 0x319c86 +14000405 NVC0_COMPUTE.0x25f4 = 0x14000405 +60325c86 NVC0_COMPUTE.0x25f8 = 0x60325c86 +14000405 NVC0_COMPUTE.0x25fc = 0x14000405 +70121c85 NVC0_COMPUTE.0x2600 = 0x70121c85 +c8000003 NVC0_COMPUTE.0x2604 = 0xc8000003 +246fdd03 NVC0_COMPUTE.0x2608 = 0x246fdd03 +200f0000 NVC0_COMPUTE.0x260c = 0x200f0000 +10221ce3 NVC0_COMPUTE.0x2610 = 0x10221ce3 +5000c000 NVC0_COMPUTE.0x2614 = 0x5000c000 +2bf1dc43 NVC0_COMPUTE.0x2618 = 0x2bf1dc43 +188e0000 NVC0_COMPUTE.0x261c = 0x188e0000 +400001e7 NVC0_COMPUTE.0x2620 = 0x400001e7 +400000cf NVC0_COMPUTE.0x2624 = 0x400000cf +3c411c03 NVC0_COMPUTE.0x2628 = 0x3c411c03 +4801c000 NVC0_COMPUTE.0x262c = 0x4801c000 +a0121ca5 NVC0_COMPUTE.0x2630 = 0xa0121ca5 +c8000003 NVC0_COMPUTE.0x2634 = 0xc8000003 +80109ca5 NVC0_COMPUTE.0x2638 = 0x80109ca5 +c8000003 NVC0_COMPUTE.0x263c = 0xc8000003 +fc01dde4 NVC0_COMPUTE.0x2640 = 0xfc01dde4 +28000000 NVC0_COMPUTE.0x2644 = 0x28000000 +fc515c43 NVC0_COMPUTE.0x2648 = 0xfc515c43 +48000000 NVC0_COMPUTE.0x264c = 0x48000000 +00010007 NVC0_COMPUTE.0x2650 = 0x10007 +100001f0 NVC0_COMPUTE.0x2654 = 0x100001f0 +70115e85 NVC0_COMPUTE.0x2658 = 0x70115e85 +c0000003 NVC0_COMPUTE.0x265c = 0xc0000003 +74201c03 NVC0_COMPUTE.0x2660 = 0x74201c03 +5800c000 NVC0_COMPUTE.0x2664 = 0x5800c000 +e000dde4 NVC0_COMPUTE.0x2668 = 0xe000dde4 +28004405 NVC0_COMPUTE.0x266c = 0x28004405 +e0000007 NVC0_COMPUTE.0x2670 = 0xe0000007 +680000cc NVC0_COMPUTE.0x2674 = 0x680000cc +20209c03 NVC0_COMPUTE.0x2678 = 0x20209c03 +2007c000 NVC0_COMPUTE.0x267c = 0x2007c000 +00501c63 NVC0_COMPUTE.0x2680 = 0x501c63 +40000000 NVC0_COMPUTE.0x2684 = 0x40000000 +0440dc03 NVC0_COMPUTE.0x2688 = 0x440dc03 +4800c000 NVC0_COMPUTE.0x268c = 0x4800c000 +fc011de4 NVC0_COMPUTE.0x2690 = 0xfc011de4 +28000000 NVC0_COMPUTE.0x2694 = 0x28000000 +f0001c43 NVC0_COMPUTE.0x2698 = 0xf0001c43 +48004405 NVC0_COMPUTE.0x269c = 0x48004405 +80109ca5 NVC0_COMPUTE.0x26a0 = 0x80109ca5 +c8000002 NVC0_COMPUTE.0x26a4 = 0xc8000002 +60111c85 NVC0_COMPUTE.0x26a8 = 0x60111c85 +c8000001 NVC0_COMPUTE.0x26ac = 0xc8000001 +30101c85 NVC0_COMPUTE.0x26b0 = 0x30101c85 +c8000001 NVC0_COMPUTE.0x26b4 = 0xc8000001 +80109c85 NVC0_COMPUTE.0x26b8 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x26bc = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x26c0 = 0x3010dc85 +c0000001 NVC0_COMPUTE.0x26c4 = 0xc0000001 +10201f85 NVC0_COMPUTE.0x26c8 = 0x10201f85 +84000000 NVC0_COMPUTE.0x26cc = 0x84000000 +20101c85 NVC0_COMPUTE.0x26d0 = 0x20101c85 +c8000001 NVC0_COMPUTE.0x26d4 = 0xc8000001 +20009c03 NVC0_COMPUTE.0x26d8 = 0x20009c03 +6000c000 NVC0_COMPUTE.0x26dc = 0x6000c000 +fc2fdd03 NVC0_COMPUTE.0x26e0 = 0xfc2fdd03 +48010000 NVC0_COMPUTE.0x26e4 = 0x48010000 +60001c03 NVC0_COMPUTE.0x26e8 = 0x60001c03 +5800c000 NVC0_COMPUTE.0x26ec = 0x5800c000 +60109c85 NVC0_COMPUTE.0x26f0 = 0x60109c85 +c8000003 NVC0_COMPUTE.0x26f4 = 0xc8000003 +fc01dc43 NVC0_COMPUTE.0x26f8 = 0xfc01dc43 +1a8e0000 NVC0_COMPUTE.0x26fc = 0x1a8e0000 +70101c85 NVC0_COMPUTE.IMAGE[0].ADDRESS_HIGH = 0x70101c85 +c8000003 NVC0_COMPUTE.IMAGE[0].ADDRESS_LOW = 0xc8000003 +c00021e7 NVC0_COMPUTE.IMAGE[0].WIDTH = 3221234151 +40000003 NVC0_COMPUTE.IMAGE[0].HEIGHT = { HEIGHT = 3 | 0x40000000 } +80101e85 NVC0_COMPUTE.IMAGE[0].FORMAT = { UNK0 | FORMAT_COLOR = B5G6R5_UNORM | FORMAT_ZETA = 0x1 | 0x80100004 } +c0000003 NVC0_COMPUTE.IMAGE[0].TILE_MODE = 0xc0000003 +60111ca5 NVC0_COMPUTE.0x2718 = 0x60111ca5 +c0000003 NVC0_COMPUTE.0x271c = 0xc0000003 +90109c85 NVC0_COMPUTE.IMAGE[0x1].ADDRESS_HIGH = 0x90109c85 +c0000002 NVC0_COMPUTE.IMAGE[0x1].ADDRESS_LOW = 0xc0000002 +80101c85 NVC0_COMPUTE.IMAGE[0x1].WIDTH = 2148539525 +c8000003 NVC0_COMPUTE.IMAGE[0x1].HEIGHT = { HEIGHT = 3 | 0xc8000000 } +00401f45 NVC0_COMPUTE.IMAGE[0x1].FORMAT = { UNK0 | FORMAT_COLOR = R8_SNORM | FORMAT_ZETA = 0x1 | 0x400004 } +84000000 NVC0_COMPUTE.IMAGE[0x1].TILE_MODE = 0x84000000 +0c03dc23 NVC0_COMPUTE.0x2738 = 0xc03dc23 +1a8ec16b NVC0_COMPUTE.0x273c = 0x1a8ec16b +e00005e7 NVC0_COMPUTE.IMAGE[0x2].ADDRESS_HIGH = 0xe00005e7 +40000002 NVC0_COMPUTE.IMAGE[0x2].ADDRESS_LOW = 0x40000002 +70101c85 NVC0_COMPUTE.IMAGE[0x2].WIDTH = 1880104069 +c0000003 NVC0_COMPUTE.IMAGE[0x2].HEIGHT = { HEIGHT = 3 | 0xc0000000 } +8010dc85 NVC0_COMPUTE.IMAGE[0x2].FORMAT = { UNK0 | FORMAT_COLOR = RGBA16_SINT | FORMAT_ZETA = 0xd | 0x80100004 } +c0000003 NVC0_COMPUTE.IMAGE[0x2].TILE_MODE = 0xc0000003 +0801dde4 NVC0_COMPUTE.0x2758 = 0x801dde4 +28000000 NVC0_COMPUTE.0x275c = 0x28000000 +00015de4 NVC0_COMPUTE.IMAGE[0x3].ADDRESS_HIGH = 0x15de4 +28000000 NVC0_COMPUTE.IMAGE[0x3].ADDRESS_LOW = 0x28000000 +60101c85 NVC0_COMPUTE.IMAGE[0x3].WIDTH = 1611668613 +c0000003 NVC0_COMPUTE.IMAGE[0x3].HEIGHT = { HEIGHT = 3 | 0xc0000000 } +0c019de4 NVC0_COMPUTE.IMAGE[0x3].FORMAT = { FORMAT_COLOR = RG16_FLOAT | FORMAT_ZETA = Z32_S8_X24_FLOAT | 0xc000004 } +28000000 NVC0_COMPUTE.IMAGE[0x3].TILE_MODE = 0x28000000 +00011de4 NVC0_COMPUTE.0x2778 = 0x11de4 +28000000 NVC0_COMPUTE.0x277c = 0x28000000 +00010007 NVC0_COMPUTE.IMAGE[0x4].ADDRESS_HIGH = 0x10007 +100001fc NVC0_COMPUTE.IMAGE[0x4].ADDRESS_LOW = 0x100001fc +fc4fdd03 NVC0_COMPUTE.IMAGE[0x4].WIDTH = 4233092355 +48010000 NVC0_COMPUTE.IMAGE[0x4].HEIGHT = { HEIGHT = 0 | UNK16 | 0x48000000 } +fc51dc43 NVC0_COMPUTE.IMAGE[0x4].FORMAT = { UNK0 | FORMAT_COLOR = RGBX32_SINT | FORMAT_ZETA = Z24_X8_S8_C8_X16_UNORM | 0xfc500002 } +190e0000 NVC0_COMPUTE.IMAGE[0x4].TILE_MODE = 0x190e0000 +000021e7 NVC0_COMPUTE.0x2798 = 0x21e7 +a8000000 NVC0_COMPUTE.0x279c = 0xa8000000 +60111ea5 NVC0_COMPUTE.IMAGE[0x5].ADDRESS_HIGH = 0x60111ea5 +c0000003 NVC0_COMPUTE.IMAGE[0x5].ADDRESS_LOW = 0xc0000003 +30401f85 NVC0_COMPUTE.IMAGE[0x5].WIDTH = 809508741 +84000000 NVC0_COMPUTE.IMAGE[0x5].HEIGHT = { HEIGHT = 0 | 0x84000000 } +20011c03 NVC0_COMPUTE.IMAGE[0x5].FORMAT = { UNK0 | FORMAT_COLOR = RGBA32_FLOAT | FORMAT_ZETA = 0x11 | 0x20000002 } +6000c000 NVC0_COMPUTE.IMAGE[0x5].TILE_MODE = 0x6000c000 +60015c03 NVC0_COMPUTE.0x27b8 = 0x60015c03 +5800c000 NVC0_COMPUTE.0x27bc = 0x5800c000 +fc4fdd03 NVC0_COMPUTE.IMAGE[0x6].ADDRESS_HIGH = 0xfc4fdd03 +48010000 NVC0_COMPUTE.IMAGE[0x6].ADDRESS_LOW = 0x48010000 +60111ca5 NVC0_COMPUTE.IMAGE[0x6].WIDTH = 1611734181 +c8000003 NVC0_COMPUTE.IMAGE[0x6].HEIGHT = { HEIGHT = 3 | 0xc8000000 } +fc51dc43 NVC0_COMPUTE.IMAGE[0x6].FORMAT = { UNK0 | FORMAT_COLOR = RGBX32_SINT | FORMAT_ZETA = Z24_X8_S8_C8_X16_UNORM | 0xfc500002 } +1a8e0000 NVC0_COMPUTE.IMAGE[0x6].TILE_MODE = 0x1a8e0000 +800021e7 NVC0_COMPUTE.0x27d8 = 0x800021e7 +40000000 NVC0_COMPUTE.0x27dc = 0x40000000 +60111ca5 NVC0_COMPUTE.IMAGE[0x7].ADDRESS_HIGH = 0x60111ca5 +c0000003 NVC0_COMPUTE.IMAGE[0x7].ADDRESS_LOW = 0xc0000003 +00401f45 NVC0_COMPUTE.IMAGE[0x7].WIDTH = 4202309 +84000000 NVC0_COMPUTE.IMAGE[0x7].HEIGHT = { HEIGHT = 0 | 0x84000000 } +0c03dc23 NVC0_COMPUTE.IMAGE[0x7].FORMAT = { UNK0 | FORMAT_COLOR = RGBA32_UINT | FORMAT_ZETA = Z24_X8_S8_C8_X16_UNORM | 0xc020002 } +190ec16b NVC0_COMPUTE.IMAGE[0x7].TILE_MODE = 0x190ec16b +200005e7 NVC0_COMPUTE.0x27f8 = 0x200005e7 +4003fffd NVC0_COMPUTE.0x27fc = 0x4003fffd +a0000007 NVC0_COMPUTE.0x2800 = 0xa0000007 +600000c5 NVC0_COMPUTE.0x2804 = 0x600000c5 +600001e7 NVC0_COMPUTE.0x2808 = 0x600001e7 +400000c5 NVC0_COMPUTE.0x280c = 0x400000c5 +00701c24 NVC0_COMPUTE.0x2810 = 0x701c24 +49c00000 NVC0_COMPUTE.0x2814 = 0x49c00000 +0000dc04 NVC0_COMPUTE.0x2818 = 0xdc04 +2c000000 NVC0_COMPUTE.0x281c = 0x2c000000 +00001c03 NVC0_COMPUTE.0x2820 = 0x1c03 +78000000 NVC0_COMPUTE.0x2824 = 0x78000000 +0c01dc03 NVC0_COMPUTE.0x2828 = 0xc01dc03 +1a8e0000 NVC0_COMPUTE.0x282c = 0x1a8e0000 +c00001e7 NVC0_COMPUTE.0x2830 = 0xc00001e7 +400000c4 NVC0_COMPUTE.0x2834 = 0x400000c4 +8010dc85 NVC0_COMPUTE.0x2838 = 0x8010dc85 +c0000003 NVC0_COMPUTE.0x283c = 0xc0000003 +00000007 NVC0_COMPUTE.0x2840 = 0x7 +600000c2 NVC0_COMPUTE.0x2844 = 0x600000c2 +c031dc03 NVC0_COMPUTE.0x2848 = 0xc031dc03 +188e4405 NVC0_COMPUTE.0x284c = 0x188e4405 +400001e7 NVC0_COMPUTE.0x2850 = 0x400001e7 +40000000 NVC0_COMPUTE.0x2854 = 0x40000000 +fc029de4 NVC0_COMPUTE.0x2858 = 0xfc029de4 +28000000 NVC0_COMPUTE.0x285c = 0x28000000 +fc02ddf4 NVC0_COMPUTE.0x2860 = 0xfc02ddf4 +28000000 NVC0_COMPUTE.0x2864 = 0x28000000 +80119c85 NVC0_COMPUTE.0x2868 = 0x80119c85 +c0000002 NVC0_COMPUTE.0x286c = 0xc0000002 +3011dc85 NVC0_COMPUTE.0x2870 = 0x3011dc85 +c0000001 NVC0_COMPUTE.0x2874 = 0xc0000001 +90101c85 NVC0_COMPUTE.0x2878 = 0x90101c85 +c0000003 NVC0_COMPUTE.0x287c = 0xc0000003 +a0111c85 NVC0_COMPUTE.0x2880 = 0xa0111c85 +c0000003 NVC0_COMPUTE.0x2884 = 0xc0000003 +80000007 NVC0_COMPUTE.0x2888 = 0x80000007 +60000003 NVC0_COMPUTE.0x288c = 0x60000003 +10619f85 NVC0_COMPUTE.0x2890 = 0x10619f85 +84000000 NVC0_COMPUTE.0x2894 = 0x84000000 +e0009c03 NVC0_COMPUTE.0x2898 = 0xe0009c03 +48014405 NVC0_COMPUTE.0x289c = 0x48014405 +f041dc43 NVC0_COMPUTE.0x28a0 = 0xf041dc43 +48004405 NVC0_COMPUTE.0x28a4 = 0x48004405 +c0211c03 NVC0_COMPUTE.0x28a8 = 0xc0211c03 +4801c000 NVC0_COMPUTE.0x28ac = 0x4801c000 +00109c85 NVC0_COMPUTE.0x28b0 = 0x109c85 +c8000001 NVC0_COMPUTE.0x28b4 = 0xc8000001 +00415c02 NVC0_COMPUTE.0x28b8 = 0x415c02 +3bfc0000 NVC0_COMPUTE.0x28bc = 0x3bfc0000 +1ff11c43 NVC0_COMPUTE.0x28c0 = 0x1ff11c43 +48000000 NVC0_COMPUTE.0x28c4 = 0x48000000 +0051dc03 NVC0_COMPUTE.0x28c8 = 0x51dc03 +190e4000 NVC0_COMPUTE.0x28cc = 0x190e4000 +fc43dc03 NVC0_COMPUTE.0x28d0 = 0xfc43dc03 +190e0000 NVC0_COMPUTE.0x28d4 = 0x190e0000 +c0211c03 NVC0_COMPUTE.0x28d8 = 0xc0211c03 +4801c000 NVC0_COMPUTE.0x28dc = 0x4801c000 +0401dc04 NVC0_COMPUTE.0x28e0 = 0x401dc04 +0c0e0000 NVC0_COMPUTE.0x28e4 = 0xc0e0000 +00111c85 NVC0_COMPUTE.0x28e8 = 0x111c85 +c8000003 NVC0_COMPUTE.0x28ec = 0xc8000003 +fc711c43 NVC0_COMPUTE.0x28f0 = 0xfc711c43 +48000000 NVC0_COMPUTE.0x28f4 = 0x48000000 +10111c85 NVC0_COMPUTE.0x28f8 = 0x10111c85 +c8000003 NVC0_COMPUTE.0x28fc = 0xc8000003 +00119ca5 NVC0_COMPUTE.0x2900 = 0x119ca5 +c8000002 NVC0_COMPUTE.0x2904 = 0xc8000002 +a00001e7 NVC0_COMPUTE.0x2908 = 0xa00001e7 +40000000 NVC0_COMPUTE.0x290c = 0x40000000 +00119c85 NVC0_COMPUTE.0x2910 = 0x119c85 +c0000001 NVC0_COMPUTE.0x2914 = 0xc0000001 +1011dc85 NVC0_COMPUTE.0x2918 = 0x1011dc85 +c0000002 NVC0_COMPUTE.0x291c = 0xc0000002 +04011de2 NVC0_COMPUTE.0x2920 = 0x4011de2 +18000000 NVC0_COMPUTE.0x2924 = 0x18000000 +c0611c05 NVC0_COMPUTE.0x2928 = 0xc0611c05 +14000000 NVC0_COMPUTE.0x292c = 0x14000000 +c0001de7 NVC0_COMPUTE.0x2930 = 0xc0001de7 +40000000 NVC0_COMPUTE.0x2934 = 0x40000000 +00119c85 NVC0_COMPUTE.0x2938 = 0x119c85 +c0000001 NVC0_COMPUTE.0x293c = 0xc0000001 +1011dc85 NVC0_COMPUTE.0x2940 = 0x1011dc85 +c0000002 NVC0_COMPUTE.0x2944 = 0xc0000002 +c0611c85 NVC0_COMPUTE.0x2948 = 0xc0611c85 +a0000000 NVC0_COMPUTE.0x294c = 0xa0000000 +04410003 NVC0_COMPUTE.0x2950 = 0x4410003 +4800c000 NVC0_COMPUTE.0x2954 = 0x4800c000 +c0610085 NVC0_COMPUTE.0x2958 = 0xc0610085 +e8000000 NVC0_COMPUTE.0x295c = 0xe8000000 +400021e7 NVC0_COMPUTE.0x2960 = 0x400021e7 +4003ffff NVC0_COMPUTE.0x2964 = 0x4003ffff +0430dc13 NVC0_COMPUTE.0x2968 = 0x430dc13 +4800c000 NVC0_COMPUTE.0x296c = 0x4800c000 +c031dc03 NVC0_COMPUTE.0x2970 = 0xc031dc03 +198e4405 NVC0_COMPUTE.0x2974 = 0x198e4405 +e010dc85 NVC0_COMPUTE.0x2978 = 0xe010dc85 +c8000000 NVC0_COMPUTE.0x297c = 0xc8000000 +600001e7 NVC0_COMPUTE.0x2980 = 0x600001e7 +40000000 NVC0_COMPUTE.0x2984 = 0x40000000 +fc011de4 NVC0_COMPUTE.0x2988 = 0xfc011de4 +28000000 NVC0_COMPUTE.0x298c = 0x28000000 +fc015de4 NVC0_COMPUTE.0x2990 = 0xfc015de4 +28000000 NVC0_COMPUTE.0x2994 = 0x28000000 +e0001de7 NVC0_COMPUTE.0x2998 = 0xe0001de7 +400000a7 NVC0_COMPUTE.0x299c = 0x400000a7 +80109c85 NVC0_COMPUTE.0x29a0 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x29a4 = 0xc0000002 +30115c85 NVC0_COMPUTE.0x29a8 = 0x30115c85 +c0000001 NVC0_COMPUTE.0x29ac = 0xc0000001 +c0001c03 NVC0_COMPUTE.0x29b0 = 0xc0001c03 +4800c004 NVC0_COMPUTE.0x29b4 = 0x4800c004 +fc00dde4 NVC0_COMPUTE.0x29b8 = 0xfc00dde4 +28000000 NVC0_COMPUTE.0x29bc = 0x28000000 +40000007 NVC0_COMPUTE.0x29c0 = 0x40000007 +680000a7 NVC0_COMPUTE.0x29c4 = 0x680000a7 +50101c85 NVC0_COMPUTE.0x29c8 = 0x50101c85 +c8000003 NVC0_COMPUTE.0x29cc = 0xc8000003 +20211c03 NVC0_COMPUTE.0x29d0 = 0x20211c03 +4801c000 NVC0_COMPUTE.0x29d4 = 0x4801c000 +5010dc85 NVC0_COMPUTE.0x29d8 = 0x5010dc85 +c8000001 NVC0_COMPUTE.0x29dc = 0xc8000001 +fc515c43 NVC0_COMPUTE.0x29e0 = 0xfc515c43 +48000000 NVC0_COMPUTE.0x29e4 = 0x48000000 +20111c85 NVC0_COMPUTE.0x29e8 = 0x20111c85 +c8000003 NVC0_COMPUTE.0x29ec = 0xc8000003 +30115c85 NVC0_COMPUTE.0x29f0 = 0x30115c85 +c8000003 NVC0_COMPUTE.0x29f4 = 0xc8000003 +80109c85 NVC0_COMPUTE.0x29f8 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x29fc = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x2a00 = 0x3010dc85 +c0000001 NVC0_COMPUTE.0x2a04 = 0xc0000001 +30201f85 NVC0_COMPUTE.0x2a08 = 0x30201f85 +84000000 NVC0_COMPUTE.0x2a0c = 0x84000000 +d0101c85 NVC0_COMPUTE.0x2a10 = 0xd0101c85 +c8000000 NVC0_COMPUTE.0x2a14 = 0xc8000000 +20009c03 NVC0_COMPUTE.0x2a18 = 0x20009c03 +6000c000 NVC0_COMPUTE.0x2a1c = 0x6000c000 +fc2fdd03 NVC0_COMPUTE.0x2a20 = 0xfc2fdd03 +48010000 NVC0_COMPUTE.0x2a24 = 0x48010000 +60001c03 NVC0_COMPUTE.0x2a28 = 0x60001c03 +5800c000 NVC0_COMPUTE.0x2a2c = 0x5800c000 +60109c85 NVC0_COMPUTE.0x2a30 = 0x60109c85 +c8000003 NVC0_COMPUTE.0x2a34 = 0xc8000003 +fc01dc43 NVC0_COMPUTE.0x2a38 = 0xfc01dc43 +1a8e0000 NVC0_COMPUTE.0x2a3c = 0x1a8e0000 +70101c85 NVC0_COMPUTE.0x2a40 = 0x70101c85 +c8000003 NVC0_COMPUTE.0x2a44 = 0xc8000003 +000021e7 NVC0_COMPUTE.0x2a48 = 0x21e7 +40000004 NVC0_COMPUTE.0x2a4c = 0x40000004 +90101e85 NVC0_COMPUTE.0x2a50 = 0x90101e85 +c0000003 NVC0_COMPUTE.0x2a54 = 0xc0000003 +60111ca5 NVC0_COMPUTE.0x2a58 = 0x60111ca5 +c0000003 NVC0_COMPUTE.0x2a5c = 0xc0000003 +e0109c85 NVC0_COMPUTE.0x2a60 = 0xe0109c85 +c0000000 NVC0_COMPUTE.0x2a64 = 0xc0000000 +90101c85 NVC0_COMPUTE.0x2a68 = 0x90101c85 +c8000003 NVC0_COMPUTE.0x2a6c = 0xc8000003 +00401f45 NVC0_COMPUTE.0x2a70 = 0x401f45 +84000000 NVC0_COMPUTE.0x2a74 = 0x84000000 +0c03dc23 NVC0_COMPUTE.0x2a78 = 0xc03dc23 +1a8ec16b NVC0_COMPUTE.0x2a7c = 0x1a8ec16b +200005e7 NVC0_COMPUTE.0x2a80 = 0x200005e7 +40000003 NVC0_COMPUTE.0x2a84 = 0x40000003 +70101c85 NVC0_COMPUTE.0x2a88 = 0x70101c85 +c0000003 NVC0_COMPUTE.0x2a8c = 0xc0000003 +08019de4 NVC0_COMPUTE.0x2a90 = 0x8019de4 +28000000 NVC0_COMPUTE.0x2a94 = 0x28000000 +0401dde2 NVC0_COMPUTE.0x2a98 = 0x401dde2 +18000000 NVC0_COMPUTE.0x2a9c = 0x18000000 +00015de4 NVC0_COMPUTE.0x2aa0 = 0x15de4 +28000000 NVC0_COMPUTE.0x2aa4 = 0x28000000 +60101c85 NVC0_COMPUTE.0x2aa8 = 0x60101c85 +c0000003 NVC0_COMPUTE.0x2aac = 0xc0000003 +00011de4 NVC0_COMPUTE.0x2ab0 = 0x11de4 +28000000 NVC0_COMPUTE.0x2ab4 = 0x28000000 +00010007 NVC0_COMPUTE.0x2ab8 = 0x10007 +100001fc NVC0_COMPUTE.0x2abc = 0x100001fc +90101c85 NVC0_COMPUTE.0x2ac0 = 0x90101c85 +c0000003 NVC0_COMPUTE.0x2ac4 = 0xc0000003 +fc4fdd03 NVC0_COMPUTE.0x2ac8 = 0xfc4fdd03 +48010000 NVC0_COMPUTE.0x2acc = 0x48010000 +fc51dc43 NVC0_COMPUTE.0x2ad0 = 0xfc51dc43 +190e0000 NVC0_COMPUTE.0x2ad4 = 0x190e0000 +60001c86 NVC0_COMPUTE.0x2ad8 = 0x60001c86 +14000405 NVC0_COMPUTE.0x2adc = 0x14000405 +b0101c85 NVC0_COMPUTE.0x2ae0 = 0xb0101c85 +c8000003 NVC0_COMPUTE.0x2ae4 = 0xc8000003 +000021e7 NVC0_COMPUTE.0x2ae8 = 0x21e7 +a8000000 NVC0_COMPUTE.0x2aec = 0xa8000000 +60111ea5 NVC0_COMPUTE.0x2af0 = 0x60111ea5 +c0000003 NVC0_COMPUTE.0x2af4 = 0xc0000003 +30401f85 NVC0_COMPUTE.0x2af8 = 0x30401f85 +84000000 NVC0_COMPUTE.0x2afc = 0x84000000 +20011c03 NVC0_COMPUTE.0x2b00 = 0x20011c03 +6000c000 NVC0_COMPUTE.0x2b04 = 0x6000c000 +60015c03 NVC0_COMPUTE.0x2b08 = 0x60015c03 +5800c000 NVC0_COMPUTE.0x2b0c = 0x5800c000 +fc4fdd03 NVC0_COMPUTE.0x2b10 = 0xfc4fdd03 +48010000 NVC0_COMPUTE.0x2b14 = 0x48010000 +60111ca5 NVC0_COMPUTE.0x2b18 = 0x60111ca5 +c8000003 NVC0_COMPUTE.0x2b1c = 0xc8000003 +fc51dc43 NVC0_COMPUTE.0x2b20 = 0xfc51dc43 +1a8e0000 NVC0_COMPUTE.0x2b24 = 0x1a8e0000 +800021e7 NVC0_COMPUTE.0x2b28 = 0x800021e7 +40000000 NVC0_COMPUTE.0x2b2c = 0x40000000 +60111ca5 NVC0_COMPUTE.0x2b30 = 0x60111ca5 +c0000003 NVC0_COMPUTE.0x2b34 = 0xc0000003 +00401f45 NVC0_COMPUTE.0x2b38 = 0x401f45 +84000000 NVC0_COMPUTE.0x2b3c = 0x84000000 +0c03dc23 NVC0_COMPUTE.0x2b40 = 0xc03dc23 +190ec16b NVC0_COMPUTE.0x2b44 = 0x190ec16b +e00005e7 NVC0_COMPUTE.0x2b48 = 0xe00005e7 +4003fffc NVC0_COMPUTE.0x2b4c = 0x4003fffc +a0000007 NVC0_COMPUTE.0x2b50 = 0xa0000007 +6000009f NVC0_COMPUTE.0x2b54 = 0x6000009f +600001e7 NVC0_COMPUTE.0x2b58 = 0x600001e7 +4000009f NVC0_COMPUTE.0x2b5c = 0x4000009f +00701c24 NVC0_COMPUTE.0x2b60 = 0x701c24 +49c00000 NVC0_COMPUTE.0x2b64 = 0x49c00000 +0000dc04 NVC0_COMPUTE.0x2b68 = 0xdc04 +2c000000 NVC0_COMPUTE.0x2b6c = 0x2c000000 +00001c03 NVC0_COMPUTE.0x2b70 = 0x1c03 +78000000 NVC0_COMPUTE.0x2b74 = 0x78000000 +0c01dc03 NVC0_COMPUTE.0x2b78 = 0xc01dc03 +1a8e0000 NVC0_COMPUTE.0x2b7c = 0x1a8e0000 +c00001e7 NVC0_COMPUTE.0x2b80 = 0xc00001e7 +4000009e NVC0_COMPUTE.0x2b84 = 0x4000009e +e0101c85 NVC0_COMPUTE.0x2b88 = 0xe0101c85 +c0000000 NVC0_COMPUTE.0x2b8c = 0xc0000000 +a0000007 NVC0_COMPUTE.0x2b90 = 0xa0000007 +6000009b NVC0_COMPUTE.0x2b94 = 0x6000009b +c001dc03 NVC0_COMPUTE.0x2b98 = 0xc001dc03 +188e4405 NVC0_COMPUTE.0x2b9c = 0x188e4405 +400001e7 NVC0_COMPUTE.0x2ba0 = 0x400001e7 +40000000 NVC0_COMPUTE.0x2ba4 = 0x40000000 +fc031de4 NVC0_COMPUTE.0x2ba8 = 0xfc031de4 +28000000 NVC0_COMPUTE.0x2bac = 0x28000000 +fc035df4 NVC0_COMPUTE.0x2bb0 = 0xfc035df4 +28000000 NVC0_COMPUTE.0x2bb4 = 0x28000000 +80109c85 NVC0_COMPUTE.0x2bb8 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x2bbc = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x2bc0 = 0x3010dc85 +c0000001 NVC0_COMPUTE.0x2bc4 = 0xc0000001 +10119c85 NVC0_COMPUTE.0x2bc8 = 0x10119c85 +c0000002 NVC0_COMPUTE.0x2bcc = 0xc0000002 +40000007 NVC0_COMPUTE.0x2bd0 = 0x40000007 +60000003 NVC0_COMPUTE.0x2bd4 = 0x60000003 +30215f85 NVC0_COMPUTE.0x2bd8 = 0x30215f85 +84000000 NVC0_COMPUTE.0x2bdc = 0x84000000 +00109c85 NVC0_COMPUTE.0x2be0 = 0x109c85 +c0000001 NVC0_COMPUTE.0x2be4 = 0xc0000001 +d0201c03 NVC0_COMPUTE.0x2be8 = 0xd0201c03 +4801c000 NVC0_COMPUTE.0x2bec = 0x4801c000 +0000dc02 NVC0_COMPUTE.0x2bf0 = 0xdc02 +3bfc0000 NVC0_COMPUTE.0x2bf4 = 0x3bfc0000 +1bf01c43 NVC0_COMPUTE.0x2bf8 = 0x1bf01c43 +48000000 NVC0_COMPUTE.0x2bfc = 0x48000000 +d0211c03 NVC0_COMPUTE.0x2c00 = 0xd0211c03 +4801c000 NVC0_COMPUTE.0x2c04 = 0x4801c000 +0031dc03 NVC0_COMPUTE.0x2c08 = 0x31dc03 +190e4000 NVC0_COMPUTE.0x2c0c = 0x190e4000 +fc03dc03 NVC0_COMPUTE.0x2c10 = 0xfc03dc03 +190e0000 NVC0_COMPUTE.0x2c14 = 0x190e0000 +fc601c43 NVC0_COMPUTE.0x2c18 = 0xfc601c43 +48000000 NVC0_COMPUTE.0x2c1c = 0x48000000 +e0111c85 NVC0_COMPUTE.0x2c20 = 0xe0111c85 +c8000002 NVC0_COMPUTE.0x2c24 = 0xc8000002 +0401dc04 NVC0_COMPUTE.0x2c28 = 0x401dc04 +0c0e0000 NVC0_COMPUTE.0x2c2c = 0xc0e0000 +f0101c85 NVC0_COMPUTE.0x2c30 = 0xf0101c85 +c8000002 NVC0_COMPUTE.0x2c34 = 0xc8000002 +b0115c85 NVC0_COMPUTE.0x2c38 = 0xb0115c85 +c8000000 NVC0_COMPUTE.0x2c3c = 0xc8000000 +a00001e7 NVC0_COMPUTE.0x2c40 = 0xa00001e7 +40000000 NVC0_COMPUTE.0x2c44 = 0x40000000 +00109c85 NVC0_COMPUTE.0x2c48 = 0x109c85 +c0000001 NVC0_COMPUTE.0x2c4c = 0xc0000001 +1010dc85 NVC0_COMPUTE.0x2c50 = 0x1010dc85 +c0000002 NVC0_COMPUTE.0x2c54 = 0xc0000002 +04001de2 NVC0_COMPUTE.0x2c58 = 0x4001de2 +18000000 NVC0_COMPUTE.0x2c5c = 0x18000000 +d0201c05 NVC0_COMPUTE.0x2c60 = 0xd0201c05 +14000000 NVC0_COMPUTE.0x2c64 = 0x14000000 +c0001de7 NVC0_COMPUTE.0x2c68 = 0xc0001de7 +40000000 NVC0_COMPUTE.0x2c6c = 0x40000000 +00109c85 NVC0_COMPUTE.0x2c70 = 0x109c85 +c0000001 NVC0_COMPUTE.0x2c74 = 0xc0000001 +1010dc85 NVC0_COMPUTE.0x2c78 = 0x1010dc85 +c0000002 NVC0_COMPUTE.0x2c7c = 0xc0000002 +d0201c85 NVC0_COMPUTE.0x2c80 = 0xd0201c85 +a0000000 NVC0_COMPUTE.0x2c84 = 0xa0000000 +04000003 NVC0_COMPUTE.0x2c88 = 0x4000003 +4800c000 NVC0_COMPUTE.0x2c8c = 0x4800c000 +d0200085 NVC0_COMPUTE.0x2c90 = 0xd0200085 +e8000000 NVC0_COMPUTE.0x2c94 = 0xe8000000 +400021e7 NVC0_COMPUTE.0x2c98 = 0x400021e7 +4003ffff NVC0_COMPUTE.0x2c9c = 0x4003ffff +00001df4 NVC0_COMPUTE.0x2ca0 = 0x1df4 +40000000 NVC0_COMPUTE.0x2ca4 = 0x40000000 +80101c85 NVC0_COMPUTE.0x2ca8 = 0x80101c85 +c0000003 NVC0_COMPUTE.0x2cac = 0xc0000003 +08001c03 NVC0_COMPUTE.0x2cb0 = 0x8001c03 +4800c000 NVC0_COMPUTE.0x2cb4 = 0x4800c000 +c001dc03 NVC0_COMPUTE.0x2cb8 = 0xc001dc03 +198e4405 NVC0_COMPUTE.0x2cbc = 0x198e4405 +a0101c85 NVC0_COMPUTE.0x2cc0 = 0xa0101c85 +c8000000 NVC0_COMPUTE.0x2cc4 = 0xc8000000 +600001e7 NVC0_COMPUTE.0x2cc8 = 0x600001e7 +40000000 NVC0_COMPUTE.0x2ccc = 0x40000000 +fc011de4 NVC0_COMPUTE.0x2cd0 = 0xfc011de4 +28000000 NVC0_COMPUTE.0x2cd4 = 0x28000000 +fc015de4 NVC0_COMPUTE.0x2cd8 = 0xfc015de4 +28000000 NVC0_COMPUTE.0x2cdc = 0x28000000 +60001de7 NVC0_COMPUTE.0x2ce0 = 0x60001de7 +40000081 NVC0_COMPUTE.0x2ce4 = 0x40000081 +80101c85 NVC0_COMPUTE.0x2ce8 = 0x80101c85 +c0000002 NVC0_COMPUTE.0x2cec = 0xc0000002 +30109c85 NVC0_COMPUTE.0x2cf0 = 0x30109c85 +c0000001 NVC0_COMPUTE.0x2cf4 = 0xc0000001 +00000007 NVC0_COMPUTE.0x2cf8 = 0x7 +68000081 NVC0_COMPUTE.0x2cfc = 0x68000081 +40011c03 NVC0_COMPUTE.0x2d00 = 0x40011c03 +4801c000 NVC0_COMPUTE.0x2d04 = 0x4801c000 +fc001de4 NVC0_COMPUTE.0x2d08 = 0xfc001de4 +28000000 NVC0_COMPUTE.0x2d0c = 0x28000000 +fc20dc43 NVC0_COMPUTE.0x2d10 = 0xfc20dc43 +48000000 NVC0_COMPUTE.0x2d14 = 0x48000000 +40101c85 NVC0_COMPUTE.0x2d18 = 0x40101c85 +c8000001 NVC0_COMPUTE.0x2d1c = 0xc8000001 +a0111c85 NVC0_COMPUTE.0x2d20 = 0xa0111c85 +c8000002 NVC0_COMPUTE.0x2d24 = 0xc8000002 +b010dc85 NVC0_COMPUTE.0x2d28 = 0xb010dc85 +c8000002 NVC0_COMPUTE.0x2d2c = 0xc8000002 +80109c85 NVC0_COMPUTE.0x2d30 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x2d34 = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x2d38 = 0x3010dc85 +c0000001 NVC0_COMPUTE.0x2d3c = 0xc0000001 +50201f85 NVC0_COMPUTE.0x2d40 = 0x50201f85 +84000000 NVC0_COMPUTE.0x2d44 = 0x84000000 +90101c85 NVC0_COMPUTE.0x2d48 = 0x90101c85 +c8000000 NVC0_COMPUTE.0x2d4c = 0xc8000000 +20009c03 NVC0_COMPUTE.0x2d50 = 0x20009c03 +6000c000 NVC0_COMPUTE.0x2d54 = 0x6000c000 +fc2fdd03 NVC0_COMPUTE.0x2d58 = 0xfc2fdd03 +48010000 NVC0_COMPUTE.0x2d5c = 0x48010000 +60001c03 NVC0_COMPUTE.0x2d60 = 0x60001c03 +5800c000 NVC0_COMPUTE.0x2d64 = 0x5800c000 +60109c85 NVC0_COMPUTE.0x2d68 = 0x60109c85 +c8000003 NVC0_COMPUTE.0x2d6c = 0xc8000003 +fc01dc43 NVC0_COMPUTE.0x2d70 = 0xfc01dc43 +1a8e0000 NVC0_COMPUTE.0x2d74 = 0x1a8e0000 +70101c85 NVC0_COMPUTE.0x2d78 = 0x70101c85 +c8000003 NVC0_COMPUTE.0x2d7c = 0xc8000003 +600021e7 NVC0_COMPUTE.0x2d80 = 0x600021e7 +40000003 NVC0_COMPUTE.0x2d84 = 0x40000003 +60111ca5 NVC0_COMPUTE.0x2d88 = 0x60111ca5 +c0000003 NVC0_COMPUTE.0x2d8c = 0xc0000003 +a0109c85 NVC0_COMPUTE.0x2d90 = 0xa0109c85 +c0000000 NVC0_COMPUTE.0x2d94 = 0xc0000000 +00401f45 NVC0_COMPUTE.0x2d98 = 0x401f45 +84000000 NVC0_COMPUTE.0x2d9c = 0x84000000 +0c03dc23 NVC0_COMPUTE.0x2da0 = 0xc03dc23 +1a8ec16b NVC0_COMPUTE.0x2da4 = 0x1a8ec16b +c00005e7 NVC0_COMPUTE.0x2da8 = 0xc00005e7 +40000002 NVC0_COMPUTE.0x2dac = 0x40000002 +70101c85 NVC0_COMPUTE.0x2db0 = 0x70101c85 +c0000003 NVC0_COMPUTE.0x2db4 = 0xc0000003 +08019de4 NVC0_COMPUTE.0x2db8 = 0x8019de4 +28000000 NVC0_COMPUTE.0x2dbc = 0x28000000 +0401dde2 NVC0_COMPUTE.0x2dc0 = 0x401dde2 +18000000 NVC0_COMPUTE.0x2dc4 = 0x18000000 +00015de4 NVC0_COMPUTE.0x2dc8 = 0x15de4 +28000000 NVC0_COMPUTE.0x2dcc = 0x28000000 +60101c85 NVC0_COMPUTE.0x2dd0 = 0x60101c85 +c0000003 NVC0_COMPUTE.0x2dd4 = 0xc0000003 +00011de4 NVC0_COMPUTE.0x2dd8 = 0x11de4 +28000000 NVC0_COMPUTE.0x2ddc = 0x28000000 +00010007 NVC0_COMPUTE.0x2de0 = 0x10007 +100001fc NVC0_COMPUTE.0x2de4 = 0x100001fc +fc4fdd03 NVC0_COMPUTE.0x2de8 = 0xfc4fdd03 +48010000 NVC0_COMPUTE.0x2dec = 0x48010000 +fc51dc43 NVC0_COMPUTE.0x2df0 = 0xfc51dc43 +190e0000 NVC0_COMPUTE.0x2df4 = 0x190e0000 +000021e7 NVC0_COMPUTE.0x2df8 = 0x21e7 +a8000000 NVC0_COMPUTE.0x2dfc = 0xa8000000 +60111ea5 NVC0_COMPUTE.0x2e00 = 0x60111ea5 +c0000003 NVC0_COMPUTE.0x2e04 = 0xc0000003 +30401f85 NVC0_COMPUTE.0x2e08 = 0x30401f85 +84000000 NVC0_COMPUTE.0x2e0c = 0x84000000 +20011c03 NVC0_COMPUTE.0x2e10 = 0x20011c03 +6000c000 NVC0_COMPUTE.0x2e14 = 0x6000c000 +60015c03 NVC0_COMPUTE.0x2e18 = 0x60015c03 +5800c000 NVC0_COMPUTE.0x2e1c = 0x5800c000 +fc4fdd03 NVC0_COMPUTE.0x2e20 = 0xfc4fdd03 +48010000 NVC0_COMPUTE.0x2e24 = 0x48010000 +60111ca5 NVC0_COMPUTE.0x2e28 = 0x60111ca5 +c8000003 NVC0_COMPUTE.0x2e2c = 0xc8000003 +fc51dc43 NVC0_COMPUTE.0x2e30 = 0xfc51dc43 +1a8e0000 NVC0_COMPUTE.0x2e34 = 0x1a8e0000 +800021e7 NVC0_COMPUTE.0x2e38 = 0x800021e7 +40000000 NVC0_COMPUTE.0x2e3c = 0x40000000 +60111ca5 NVC0_COMPUTE.0x2e40 = 0x60111ca5 +c0000003 NVC0_COMPUTE.0x2e44 = 0xc0000003 +00401f45 NVC0_COMPUTE.0x2e48 = 0x401f45 +84000000 NVC0_COMPUTE.0x2e4c = 0x84000000 +0c03dc23 NVC0_COMPUTE.0x2e50 = 0xc03dc23 +190ec16b NVC0_COMPUTE.0x2e54 = 0x190ec16b +400005e7 NVC0_COMPUTE.0x2e58 = 0x400005e7 +4003fffd NVC0_COMPUTE.0x2e5c = 0x4003fffd +60000007 NVC0_COMPUTE.0x2e60 = 0x60000007 +6000007a NVC0_COMPUTE.0x2e64 = 0x6000007a +200001e7 NVC0_COMPUTE.0x2e68 = 0x200001e7 +4000007a NVC0_COMPUTE.0x2e6c = 0x4000007a +00701c24 NVC0_COMPUTE.0x2e70 = 0x701c24 +49c00000 NVC0_COMPUTE.0x2e74 = 0x49c00000 +0000dc04 NVC0_COMPUTE.0x2e78 = 0xdc04 +2c000000 NVC0_COMPUTE.0x2e7c = 0x2c000000 +00001c03 NVC0_COMPUTE.0x2e80 = 0x1c03 +78000000 NVC0_COMPUTE.0x2e84 = 0x78000000 +0c01dc03 NVC0_COMPUTE.0x2e88 = 0xc01dc03 +1a8e0000 NVC0_COMPUTE.0x2e8c = 0x1a8e0000 +800001e7 NVC0_COMPUTE.0x2e90 = 0x800001e7 +40000079 NVC0_COMPUTE.0x2e94 = 0x40000079 +a0101c85 NVC0_COMPUTE.0x2e98 = 0xa0101c85 +c0000000 NVC0_COMPUTE.0x2e9c = 0xc0000000 +c0000007 NVC0_COMPUTE.0x2ea0 = 0xc0000007 +60000076 NVC0_COMPUTE.0x2ea4 = 0x60000076 +c001dc03 NVC0_COMPUTE.0x2ea8 = 0xc001dc03 +188e4405 NVC0_COMPUTE.0x2eac = 0x188e4405 +400001e7 NVC0_COMPUTE.0x2eb0 = 0x400001e7 +40000000 NVC0_COMPUTE.0x2eb4 = 0x40000000 +fc031de4 NVC0_COMPUTE.0x2eb8 = 0xfc031de4 +28000000 NVC0_COMPUTE.0x2ebc = 0x28000000 +fc035df4 NVC0_COMPUTE.0x2ec0 = 0xfc035df4 +28000000 NVC0_COMPUTE.0x2ec4 = 0x28000000 +80109c85 NVC0_COMPUTE.0x2ec8 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x2ecc = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x2ed0 = 0x3010dc85 +c0000001 NVC0_COMPUTE.0x2ed4 = 0xc0000001 +10119c85 NVC0_COMPUTE.0x2ed8 = 0x10119c85 +c0000002 NVC0_COMPUTE.0x2edc = 0xc0000002 +40000007 NVC0_COMPUTE.0x2ee0 = 0x40000007 +60000003 NVC0_COMPUTE.0x2ee4 = 0x60000003 +50215f85 NVC0_COMPUTE.0x2ee8 = 0x50215f85 +84000000 NVC0_COMPUTE.0x2eec = 0x84000000 +00109c85 NVC0_COMPUTE.0x2ef0 = 0x109c85 +c0000001 NVC0_COMPUTE.0x2ef4 = 0xc0000001 +e0201c03 NVC0_COMPUTE.0x2ef8 = 0xe0201c03 +4801c000 NVC0_COMPUTE.0x2efc = 0x4801c000 +0000dc02 NVC0_COMPUTE.0x2f00 = 0xdc02 +3bfc0000 NVC0_COMPUTE.0x2f04 = 0x3bfc0000 +1bf01c43 NVC0_COMPUTE.0x2f08 = 0x1bf01c43 +48000000 NVC0_COMPUTE.0x2f0c = 0x48000000 +e0211c03 NVC0_COMPUTE.0x2f10 = 0xe0211c03 +4801c000 NVC0_COMPUTE.0x2f14 = 0x4801c000 +0031dc03 NVC0_COMPUTE.0x2f18 = 0x31dc03 +190e4000 NVC0_COMPUTE.0x2f1c = 0x190e4000 +fc03dc03 NVC0_COMPUTE.0x2f20 = 0xfc03dc03 +190e0000 NVC0_COMPUTE.0x2f24 = 0x190e0000 +fc601c43 NVC0_COMPUTE.0x2f28 = 0xfc601c43 +48000000 NVC0_COMPUTE.0x2f2c = 0x48000000 +60111c85 NVC0_COMPUTE.0x2f30 = 0x60111c85 +c8000002 NVC0_COMPUTE.0x2f34 = 0xc8000002 +0401dc04 NVC0_COMPUTE.0x2f38 = 0x401dc04 +0c0e0000 NVC0_COMPUTE.0x2f3c = 0xc0e0000 +70101c85 NVC0_COMPUTE.0x2f40 = 0x70101c85 +c8000002 NVC0_COMPUTE.0x2f44 = 0xc8000002 +80115c85 NVC0_COMPUTE.0x2f48 = 0x80115c85 +c8000000 NVC0_COMPUTE.0x2f4c = 0xc8000000 +a00001e7 NVC0_COMPUTE.0x2f50 = 0xa00001e7 +40000000 NVC0_COMPUTE.0x2f54 = 0x40000000 +00109c85 NVC0_COMPUTE.0x2f58 = 0x109c85 +c0000001 NVC0_COMPUTE.0x2f5c = 0xc0000001 +1010dc85 NVC0_COMPUTE.0x2f60 = 0x1010dc85 +c0000002 NVC0_COMPUTE.0x2f64 = 0xc0000002 +04001de2 NVC0_COMPUTE.0x2f68 = 0x4001de2 +18000000 NVC0_COMPUTE.0x2f6c = 0x18000000 +e0201c05 NVC0_COMPUTE.0x2f70 = 0xe0201c05 +14000000 NVC0_COMPUTE.0x2f74 = 0x14000000 +c0001de7 NVC0_COMPUTE.0x2f78 = 0xc0001de7 +40000000 NVC0_COMPUTE.0x2f7c = 0x40000000 +00109c85 NVC0_COMPUTE.0x2f80 = 0x109c85 +c0000001 NVC0_COMPUTE.0x2f84 = 0xc0000001 +1010dc85 NVC0_COMPUTE.0x2f88 = 0x1010dc85 +c0000002 NVC0_COMPUTE.0x2f8c = 0xc0000002 +e0201c85 NVC0_COMPUTE.0x2f90 = 0xe0201c85 +a0000000 NVC0_COMPUTE.0x2f94 = 0xa0000000 +04000003 NVC0_COMPUTE.0x2f98 = 0x4000003 +4800c000 NVC0_COMPUTE.0x2f9c = 0x4800c000 +e0200085 NVC0_COMPUTE.0x2fa0 = 0xe0200085 +e8000000 NVC0_COMPUTE.0x2fa4 = 0xe8000000 +400021e7 NVC0_COMPUTE.0x2fa8 = 0x400021e7 +4003ffff NVC0_COMPUTE.0x2fac = 0x4003ffff +00001df4 NVC0_COMPUTE.0x2fb0 = 0x1df4 +40000000 NVC0_COMPUTE.0x2fb4 = 0x40000000 +80101c85 NVC0_COMPUTE.0x2fb8 = 0x80101c85 +c0000003 NVC0_COMPUTE.0x2fbc = 0xc0000003 +0c001c03 NVC0_COMPUTE.0x2fc0 = 0xc001c03 +4800c000 NVC0_COMPUTE.0x2fc4 = 0x4800c000 +c001dc03 NVC0_COMPUTE.0x2fc8 = 0xc001dc03 +198e4405 NVC0_COMPUTE.0x2fcc = 0x198e4405 +70101c85 NVC0_COMPUTE.0x2fd0 = 0x70101c85 +c8000000 NVC0_COMPUTE.0x2fd4 = 0xc8000000 +600001e7 NVC0_COMPUTE.0x2fd8 = 0x600001e7 +40000000 NVC0_COMPUTE.0x2fdc = 0x40000000 +fc011de4 NVC0_COMPUTE.0x2fe0 = 0xfc011de4 +28000000 NVC0_COMPUTE.0x2fe4 = 0x28000000 +fc015de4 NVC0_COMPUTE.0x2fe8 = 0xfc015de4 +28000000 NVC0_COMPUTE.0x2fec = 0x28000000 +80001de7 NVC0_COMPUTE.0x2ff0 = 0x80001de7 +4000005c NVC0_COMPUTE.0x2ff4 = 0x4000005c +80101c85 NVC0_COMPUTE.0x2ff8 = 0x80101c85 +c0000002 NVC0_COMPUTE.0x2ffc = 0xc0000002 +30109c85 NVC0_COMPUTE.0x3000 = 0x30109c85 +c0000001 NVC0_COMPUTE.0x3004 = 0xc0000001 +20000007 NVC0_COMPUTE.0x3008 = 0x20000007 +6800005c NVC0_COMPUTE.0x300c = 0x6800005c +60011c03 NVC0_COMPUTE.0x3010 = 0x60011c03 +4801c000 NVC0_COMPUTE.0x3014 = 0x4801c000 +fc001de4 NVC0_COMPUTE.0x3018 = 0xfc001de4 +28000000 NVC0_COMPUTE.0x301c = 0x28000000 +fc20dc43 NVC0_COMPUTE.0x3020 = 0xfc20dc43 +48000000 NVC0_COMPUTE.0x3024 = 0x48000000 +10101c85 NVC0_COMPUTE.0x3028 = 0x10101c85 +c8000001 NVC0_COMPUTE.0x302c = 0xc8000001 +40111c85 NVC0_COMPUTE.0x3030 = 0x40111c85 +c8000002 NVC0_COMPUTE.0x3034 = 0xc8000002 +5010dc85 NVC0_COMPUTE.0x3038 = 0x5010dc85 +c8000002 NVC0_COMPUTE.0x303c = 0xc8000002 +80109c85 NVC0_COMPUTE.0x3040 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x3044 = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x3048 = 0x3010dc85 +c0000001 NVC0_COMPUTE.0x304c = 0xc0000001 +70201f85 NVC0_COMPUTE.0x3050 = 0x70201f85 +84000000 NVC0_COMPUTE.0x3054 = 0x84000000 +60101c85 NVC0_COMPUTE.0x3058 = 0x60101c85 +c8000000 NVC0_COMPUTE.0x305c = 0xc8000000 +20009c03 NVC0_COMPUTE.0x3060 = 0x20009c03 +6000c000 NVC0_COMPUTE.0x3064 = 0x6000c000 +fc2fdd03 NVC0_COMPUTE.0x3068 = 0xfc2fdd03 +48010000 NVC0_COMPUTE.0x306c = 0x48010000 +60001c03 NVC0_COMPUTE.0x3070 = 0x60001c03 +5800c000 NVC0_COMPUTE.0x3074 = 0x5800c000 +60109c85 NVC0_COMPUTE.0x3078 = 0x60109c85 +c8000003 NVC0_COMPUTE.0x307c = 0xc8000003 +fc01dc43 NVC0_COMPUTE.0x3080 = 0xfc01dc43 +1a8e0000 NVC0_COMPUTE.0x3084 = 0x1a8e0000 +70101c85 NVC0_COMPUTE.0x3088 = 0x70101c85 +c8000003 NVC0_COMPUTE.0x308c = 0xc8000003 +600021e7 NVC0_COMPUTE.0x3090 = 0x600021e7 +40000003 NVC0_COMPUTE.0x3094 = 0x40000003 +60111ca5 NVC0_COMPUTE.0x3098 = 0x60111ca5 +c0000003 NVC0_COMPUTE.0x309c = 0xc0000003 +70109c85 NVC0_COMPUTE.0x30a0 = 0x70109c85 +c0000000 NVC0_COMPUTE.0x30a4 = 0xc0000000 +00401f45 NVC0_COMPUTE.0x30a8 = 0x401f45 +84000000 NVC0_COMPUTE.0x30ac = 0x84000000 +0c03dc23 NVC0_COMPUTE.0x30b0 = 0xc03dc23 +1a8ec16b NVC0_COMPUTE.0x30b4 = 0x1a8ec16b +c00005e7 NVC0_COMPUTE.0x30b8 = 0xc00005e7 +40000002 NVC0_COMPUTE.0x30bc = 0x40000002 +70101c85 NVC0_COMPUTE.0x30c0 = 0x70101c85 +c0000003 NVC0_COMPUTE.0x30c4 = 0xc0000003 +08019de4 NVC0_COMPUTE.0x30c8 = 0x8019de4 +28000000 NVC0_COMPUTE.0x30cc = 0x28000000 +0401dde2 NVC0_COMPUTE.0x30d0 = 0x401dde2 +18000000 NVC0_COMPUTE.0x30d4 = 0x18000000 +00015de4 NVC0_COMPUTE.0x30d8 = 0x15de4 +28000000 NVC0_COMPUTE.0x30dc = 0x28000000 +60101c85 NVC0_COMPUTE.0x30e0 = 0x60101c85 +c0000003 NVC0_COMPUTE.0x30e4 = 0xc0000003 +00011de4 NVC0_COMPUTE.0x30e8 = 0x11de4 +28000000 NVC0_COMPUTE.0x30ec = 0x28000000 +00010007 NVC0_COMPUTE.0x30f0 = 0x10007 +100001fc NVC0_COMPUTE.0x30f4 = 0x100001fc +fc4fdd03 NVC0_COMPUTE.0x30f8 = 0xfc4fdd03 +48010000 NVC0_COMPUTE.0x30fc = 0x48010000 +fc51dc43 NVC0_COMPUTE.0x3100 = 0xfc51dc43 +190e0000 NVC0_COMPUTE.0x3104 = 0x190e0000 +000021e7 NVC0_COMPUTE.0x3108 = 0x21e7 +a8000000 NVC0_COMPUTE.0x310c = 0xa8000000 +60111ea5 NVC0_COMPUTE.0x3110 = 0x60111ea5 +c0000003 NVC0_COMPUTE.0x3114 = 0xc0000003 +30401f85 NVC0_COMPUTE.0x3118 = 0x30401f85 +84000000 NVC0_COMPUTE.0x311c = 0x84000000 +20011c03 NVC0_COMPUTE.0x3120 = 0x20011c03 +6000c000 NVC0_COMPUTE.0x3124 = 0x6000c000 +60015c03 NVC0_COMPUTE.0x3128 = 0x60015c03 +5800c000 NVC0_COMPUTE.0x312c = 0x5800c000 +fc4fdd03 NVC0_COMPUTE.0x3130 = 0xfc4fdd03 +48010000 NVC0_COMPUTE.0x3134 = 0x48010000 +60111ca5 NVC0_COMPUTE.0x3138 = 0x60111ca5 +c8000003 NVC0_COMPUTE.0x313c = 0xc8000003 +fc51dc43 NVC0_COMPUTE.0x3140 = 0xfc51dc43 +1a8e0000 NVC0_COMPUTE.0x3144 = 0x1a8e0000 +800021e7 NVC0_COMPUTE.0x3148 = 0x800021e7 +40000000 NVC0_COMPUTE.0x314c = 0x40000000 +60111ca5 NVC0_COMPUTE.0x3150 = 0x60111ca5 +c0000003 NVC0_COMPUTE.0x3154 = 0xc0000003 +00401f45 NVC0_COMPUTE.0x3158 = 0x401f45 +84000000 NVC0_COMPUTE.0x315c = 0x84000000 +0c03dc23 NVC0_COMPUTE.0x3160 = 0xc03dc23 +190ec16b NVC0_COMPUTE.0x3164 = 0x190ec16b +400005e7 NVC0_COMPUTE.0x3168 = 0x400005e7 +4003fffd NVC0_COMPUTE.0x316c = 0x4003fffd +80000007 NVC0_COMPUTE.0x3170 = 0x80000007 +60000055 NVC0_COMPUTE.0x3174 = 0x60000055 +400001e7 NVC0_COMPUTE.0x3178 = 0x400001e7 +40000055 NVC0_COMPUTE.0x317c = 0x40000055 +00701c24 NVC0_COMPUTE.0x3180 = 0x701c24 +49c00000 NVC0_COMPUTE.0x3184 = 0x49c00000 +0000dc04 NVC0_COMPUTE.0x3188 = 0xdc04 +2c000000 NVC0_COMPUTE.0x318c = 0x2c000000 +00001c03 NVC0_COMPUTE.0x3190 = 0x1c03 +78000000 NVC0_COMPUTE.0x3194 = 0x78000000 +0c01dc03 NVC0_COMPUTE.0x3198 = 0xc01dc03 +1a8e0000 NVC0_COMPUTE.0x319c = 0x1a8e0000 +a00001e7 NVC0_COMPUTE.0x31a0 = 0xa00001e7 +40000054 NVC0_COMPUTE.0x31a4 = 0x40000054 +70101c85 NVC0_COMPUTE.0x31a8 = 0x70101c85 +c0000000 NVC0_COMPUTE.0x31ac = 0xc0000000 +e0000007 NVC0_COMPUTE.0x31b0 = 0xe0000007 +60000051 NVC0_COMPUTE.0x31b4 = 0x60000051 +c001dc03 NVC0_COMPUTE.0x31b8 = 0xc001dc03 +188e4405 NVC0_COMPUTE.0x31bc = 0x188e4405 +400001e7 NVC0_COMPUTE.0x31c0 = 0x400001e7 +40000000 NVC0_COMPUTE.0x31c4 = 0x40000000 +fc031de4 NVC0_COMPUTE.0x31c8 = 0xfc031de4 +28000000 NVC0_COMPUTE.0x31cc = 0x28000000 +fc035df4 NVC0_COMPUTE.0x31d0 = 0xfc035df4 +28000000 NVC0_COMPUTE.0x31d4 = 0x28000000 +80109c85 NVC0_COMPUTE.0x31d8 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x31dc = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x31e0 = 0x3010dc85 +c0000001 NVC0_COMPUTE.0x31e4 = 0xc0000001 +10119c85 NVC0_COMPUTE.0x31e8 = 0x10119c85 +c0000002 NVC0_COMPUTE.0x31ec = 0xc0000002 +40000007 NVC0_COMPUTE.0x31f0 = 0x40000007 +60000003 NVC0_COMPUTE.0x31f4 = 0x60000003 +70215f85 NVC0_COMPUTE.0x31f8 = 0x70215f85 +84000000 NVC0_COMPUTE.0x31fc = 0x84000000 +00109c85 NVC0_COMPUTE.0x3200 = 0x109c85 +c0000001 NVC0_COMPUTE.0x3204 = 0xc0000001 +f0201c03 NVC0_COMPUTE.0x3208 = 0xf0201c03 +4801c000 NVC0_COMPUTE.0x320c = 0x4801c000 +0000dc02 NVC0_COMPUTE.0x3210 = 0xdc02 +3bfc0000 NVC0_COMPUTE.0x3214 = 0x3bfc0000 +1bf01c43 NVC0_COMPUTE.0x3218 = 0x1bf01c43 +48000000 NVC0_COMPUTE.0x321c = 0x48000000 +f0211c03 NVC0_COMPUTE.0x3220 = 0xf0211c03 +4801c000 NVC0_COMPUTE.0x3224 = 0x4801c000 +0031dc03 NVC0_COMPUTE.0x3228 = 0x31dc03 +190e4000 NVC0_COMPUTE.0x322c = 0x190e4000 +fc03dc03 NVC0_COMPUTE.0x3230 = 0xfc03dc03 +190e0000 NVC0_COMPUTE.0x3234 = 0x190e0000 +fc601c43 NVC0_COMPUTE.0x3238 = 0xfc601c43 +48000000 NVC0_COMPUTE.0x323c = 0x48000000 +20111c85 NVC0_COMPUTE.0x3240 = 0x20111c85 +c8000002 NVC0_COMPUTE.0x3244 = 0xc8000002 +0401dc04 NVC0_COMPUTE.0x3248 = 0x401dc04 +0c0e0000 NVC0_COMPUTE.0x324c = 0xc0e0000 +30101c85 NVC0_COMPUTE.0x3250 = 0x30101c85 +c8000002 NVC0_COMPUTE.0x3254 = 0xc8000002 +50115c85 NVC0_COMPUTE.0x3258 = 0x50115c85 +c8000000 NVC0_COMPUTE.0x325c = 0xc8000000 +a00001e7 NVC0_COMPUTE.0x3260 = 0xa00001e7 +40000000 NVC0_COMPUTE.0x3264 = 0x40000000 +00109c85 NVC0_COMPUTE.0x3268 = 0x109c85 +c0000001 NVC0_COMPUTE.0x326c = 0xc0000001 +1010dc85 NVC0_COMPUTE.0x3270 = 0x1010dc85 +c0000002 NVC0_COMPUTE.0x3274 = 0xc0000002 +04001de2 NVC0_COMPUTE.0x3278 = 0x4001de2 +18000000 NVC0_COMPUTE.0x327c = 0x18000000 +f0201c05 NVC0_COMPUTE.0x3280 = 0xf0201c05 +14000000 NVC0_COMPUTE.0x3284 = 0x14000000 +c0001de7 NVC0_COMPUTE.0x3288 = 0xc0001de7 +40000000 NVC0_COMPUTE.0x328c = 0x40000000 +00109c85 NVC0_COMPUTE.0x3290 = 0x109c85 +c0000001 NVC0_COMPUTE.0x3294 = 0xc0000001 +1010dc85 NVC0_COMPUTE.0x3298 = 0x1010dc85 +c0000002 NVC0_COMPUTE.0x329c = 0xc0000002 +f0201c85 NVC0_COMPUTE.0x32a0 = 0xf0201c85 +a0000000 NVC0_COMPUTE.0x32a4 = 0xa0000000 +04000003 NVC0_COMPUTE.0x32a8 = 0x4000003 +4800c000 NVC0_COMPUTE.0x32ac = 0x4800c000 +f0200085 NVC0_COMPUTE.0x32b0 = 0xf0200085 +e8000000 NVC0_COMPUTE.0x32b4 = 0xe8000000 +400021e7 NVC0_COMPUTE.0x32b8 = 0x400021e7 +4003ffff NVC0_COMPUTE.0x32bc = 0x4003ffff +00001df4 NVC0_COMPUTE.0x32c0 = 0x1df4 +40000000 NVC0_COMPUTE.0x32c4 = 0x40000000 +80101c85 NVC0_COMPUTE.0x32c8 = 0x80101c85 +c0000003 NVC0_COMPUTE.0x32cc = 0xc0000003 +10001c03 NVC0_COMPUTE.0x32d0 = 0x10001c03 +4800c000 NVC0_COMPUTE.0x32d4 = 0x4800c000 +c001dc03 NVC0_COMPUTE.0x32d8 = 0xc001dc03 +198e4405 NVC0_COMPUTE.0x32dc = 0x198e4405 +40101c85 NVC0_COMPUTE.0x32e0 = 0x40101c85 +c8000003 NVC0_COMPUTE.0x32e4 = 0xc8000003 +600001e7 NVC0_COMPUTE.0x32e8 = 0x600001e7 +40000000 NVC0_COMPUTE.0x32ec = 0x40000000 +fc011de4 NVC0_COMPUTE.0x32f0 = 0xfc011de4 +28000000 NVC0_COMPUTE.0x32f4 = 0x28000000 +fc015de4 NVC0_COMPUTE.0x32f8 = 0xfc015de4 +28000000 NVC0_COMPUTE.0x32fc = 0x28000000 +a0001de7 NVC0_COMPUTE.0x3300 = 0xa0001de7 +40000037 NVC0_COMPUTE.0x3304 = 0x40000037 +80101c85 NVC0_COMPUTE.0x3308 = 0x80101c85 +c0000002 NVC0_COMPUTE.0x330c = 0xc0000002 +30109c85 NVC0_COMPUTE.0x3310 = 0x30109c85 +c0000001 NVC0_COMPUTE.0x3314 = 0xc0000001 +40000007 NVC0_COMPUTE.0x3318 = 0x40000007 +68000037 NVC0_COMPUTE.0x331c = 0x68000037 +80001c03 NVC0_COMPUTE.0x3320 = 0x80001c03 +4801c000 NVC0_COMPUTE.0x3324 = 0x4801c000 +e0101c85 NVC0_COMPUTE.0x3328 = 0xe0101c85 +c8000001 NVC0_COMPUTE.0x332c = 0xc8000001 +fc209c43 NVC0_COMPUTE.0x3330 = 0xfc209c43 +48000000 NVC0_COMPUTE.0x3334 = 0x48000000 +fc001de4 NVC0_COMPUTE.0x3338 = 0xfc001de4 +28000000 NVC0_COMPUTE.0x333c = 0x28000000 +f0109c85 NVC0_COMPUTE.0x3340 = 0xf0109c85 +c8000001 NVC0_COMPUTE.0x3344 = 0xc8000001 +f0101c85 NVC0_COMPUTE.0x3348 = 0xf0101c85 +c8000000 NVC0_COMPUTE.0x334c = 0xc8000000 +80109c85 NVC0_COMPUTE.0x3350 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x3354 = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x3358 = 0x3010dc85 +c0000001 NVC0_COMPUTE.PM_SET[0] = 0xc0000001 +90201f85 NVC0_COMPUTE.PM_SET[0x1] = 0x90201f85 +84000000 NVC0_COMPUTE.PM_SET[0x2] = 0x84000000 +40101c85 NVC0_COMPUTE.PM_SET[0x3] = 0x40101c85 +c8000000 NVC0_COMPUTE.PM_SET[0x4] = 0xc8000000 +20009c03 NVC0_COMPUTE.PM_SET[0x5] = 0x20009c03 +6000c000 NVC0_COMPUTE.PM_SET[0x6] = 0x6000c000 +fc2fdd03 NVC0_COMPUTE.PM_SET[0x7] = 0xfc2fdd03 +48010000 NVC0_COMPUTE.PM_UNK337C[0] = 0x48010000 +60001c03 NVC0_COMPUTE.PM_UNK337C[0x1] = 0x60001c03 +5800c000 NVC0_COMPUTE.PM_UNK337C[0x2] = 0x5800c000 +60109c85 NVC0_COMPUTE.PM_UNK337C[0x3] = 0x60109c85 +c8000003 NVC0_COMPUTE.PM_UNK337C[0x4] = 0xc8000003 +fc01dc43 NVC0_COMPUTE.PM_UNK337C[0x5] = 0xfc01dc43 +1a8e0000 NVC0_COMPUTE.PM_UNK337C[0x6] = 0x1a8e0000 +70101c85 NVC0_COMPUTE.PM_UNK337C[0x7] = 0x70101c85 +c8000003 NVC0_COMPUTE.PM_UNK339C[0] = { 0 = 0x3 | 1 = 0 | 2 = 0 | 3 = 0 | 4 = 0 | 5 = 0 | 6 = 0 | 7 = 0x4 | 0x88000000 } +600021e7 NVC0_COMPUTE.PM_UNK339C[0x1] = { 0 = 0x7 | 1 = 0x6 | 2 = 0x1 | 3 = 0x2 | 4 = 0 | 5 = 0 | 6 = 0 | 7 = 0x6 | 0x80 } +40000003 NVC0_COMPUTE.PM_UNK339C[0x2] = { 0 = 0x3 | 1 = 0 | 2 = 0 | 3 = 0 | 4 = 0 | 5 = 0 | 6 = 0 | 7 = 0x4 } +60111ca5 NVC0_COMPUTE.PM_UNK339C[0x3] = { 0 = 0x5 | 1 = 0x2 | 2 = 0x4 | 3 = 0x1 | 4 = 0x1 | 5 = 0x1 | 6 = 0 | 7 = 0x6 | 0x880 } +c0000003 NVC0_COMPUTE.PM_UNK339C[0x4] = { 0 = 0x3 | 1 = 0 | 2 = 0 | 3 = 0 | 4 = 0 | 5 = 0 | 6 = 0 | 7 = 0x4 | 0x80000000 } +40109c85 NVC0_COMPUTE.PM_UNK339C[0x5] = { 0 = 0x5 | 1 = 0 | 2 = 0x4 | 3 = 0x1 | 4 = 0 | 5 = 0x1 | 6 = 0 | 7 = 0x4 | 0x8880 } +c0000003 NVC0_COMPUTE.PM_UNK339C[0x6] = { 0 = 0x3 | 1 = 0 | 2 = 0 | 3 = 0 | 4 = 0 | 5 = 0 | 6 = 0 | 7 = 0x4 | 0x80000000 } +00401f45 NVC0_COMPUTE.PM_UNK339C[0x7] = { 0 = 0x5 | 1 = 0x4 | 2 = 0x7 | 3 = 0x1 | 4 = 0 | 5 = 0x4 | 6 = 0 | 7 = 0 | 0x800 } +84000000 NVC0_COMPUTE.PM_UNK33BC[0] = { 4 = 0 | 0x84000000 } +0c03dc23 NVC0_COMPUTE.PM_UNK33BC[0x1] = { 0 | 4 = 0xdc2 | 0xc030002 } +1a8ec16b NVC0_COMPUTE.PM_UNK33BC[0x2] = { 0 | 4 = 0xc16 | 0x1a8e000a } +c00005e7 NVC0_COMPUTE.PM_UNK33BC[0x3] = { 0 | 4 = 0x5e | 0xc0000006 } +40000002 NVC0_COMPUTE.PM_UNK33BC[0x4] = { 4 = 0 | 0x40000002 } +70101c85 NVC0_COMPUTE.PM_UNK33BC[0x5] = { 0 | 4 = 0x1c8 | 0x70100004 } +c0000003 NVC0_COMPUTE.PM_UNK33BC[0x6] = { 0 | 4 = 0 | 0xc0000002 } +08019de4 NVC0_COMPUTE.PM_UNK33BC[0x7] = { 4 = 0x9de | 0x8010004 } +28000000 NVC0_COMPUTE.PM_UNK33DC = 0x28000000 +0401dde2 NVC0_COMPUTE.0x33e0 = 0x401dde2 +18000000 NVC0_COMPUTE.0x33e4 = 0x18000000 +00015de4 NVC0_COMPUTE.0x33e8 = 0x15de4 +28000000 NVC0_COMPUTE.0x33ec = 0x28000000 +60101c85 NVC0_COMPUTE.0x33f0 = 0x60101c85 +c0000003 NVC0_COMPUTE.0x33f4 = 0xc0000003 +00011de4 NVC0_COMPUTE.0x33f8 = 0x11de4 +28000000 NVC0_COMPUTE.0x33fc = 0x28000000 +00010007 NVC0_COMPUTE.GRAPH.SCRATCH[0] = 0x10007 +100001fc NVC0_COMPUTE.GRAPH.SCRATCH[0x1] = 0x100001fc +fc4fdd03 NVC0_COMPUTE.GRAPH.SCRATCH[0x2] = 0xfc4fdd03 +48010000 NVC0_COMPUTE.GRAPH.SCRATCH[0x3] = 0x48010000 +fc51dc43 NVC0_COMPUTE.GRAPH.SCRATCH[0x4] = 0xfc51dc43 +190e0000 NVC0_COMPUTE.GRAPH.SCRATCH[0x5] = 0x190e0000 +000021e7 NVC0_COMPUTE.GRAPH.SCRATCH[0x6] = 0x21e7 +a8000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x7] = 0xa8000000 +60111ea5 NVC0_COMPUTE.GRAPH.SCRATCH[0x8] = 0x60111ea5 +c0000003 NVC0_COMPUTE.GRAPH.SCRATCH[0x9] = 0xc0000003 +30401f85 NVC0_COMPUTE.GRAPH.SCRATCH[0xa] = 0x30401f85 +84000000 NVC0_COMPUTE.GRAPH.SCRATCH[0xb] = 0x84000000 +20011c03 NVC0_COMPUTE.GRAPH.SCRATCH[0xc] = 0x20011c03 +6000c000 NVC0_COMPUTE.GRAPH.SCRATCH[0xd] = 0x6000c000 +60015c03 NVC0_COMPUTE.GRAPH.SCRATCH[0xe] = 0x60015c03 +5800c000 NVC0_COMPUTE.GRAPH.SCRATCH[0xf] = 0x5800c000 +fc4fdd03 NVC0_COMPUTE.GRAPH.SCRATCH[0x10] = 0xfc4fdd03 +48010000 NVC0_COMPUTE.GRAPH.SCRATCH[0x11] = 0x48010000 +60111ca5 NVC0_COMPUTE.GRAPH.SCRATCH[0x12] = 0x60111ca5 +c8000003 NVC0_COMPUTE.GRAPH.SCRATCH[0x13] = 0xc8000003 +fc51dc43 NVC0_COMPUTE.GRAPH.SCRATCH[0x14] = 0xfc51dc43 +1a8e0000 NVC0_COMPUTE.GRAPH.SCRATCH[0x15] = 0x1a8e0000 +800021e7 NVC0_COMPUTE.GRAPH.SCRATCH[0x16] = 0x800021e7 +40000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x17] = 0x40000000 +60111ca5 NVC0_COMPUTE.GRAPH.SCRATCH[0x18] = 0x60111ca5 +c0000003 NVC0_COMPUTE.GRAPH.SCRATCH[0x19] = 0xc0000003 +00401f45 NVC0_COMPUTE.GRAPH.SCRATCH[0x1a] = 0x401f45 +84000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x1b] = 0x84000000 +0c03dc23 NVC0_COMPUTE.GRAPH.SCRATCH[0x1c] = 0xc03dc23 +190ec16b NVC0_COMPUTE.GRAPH.SCRATCH[0x1d] = 0x190ec16b +400005e7 NVC0_COMPUTE.GRAPH.SCRATCH[0x1e] = 0x400005e7 +4003fffd NVC0_COMPUTE.GRAPH.SCRATCH[0x1f] = 0x4003fffd +a0000007 NVC0_COMPUTE.GRAPH.SCRATCH[0x20] = 0xa0000007 +60000030 NVC0_COMPUTE.GRAPH.SCRATCH[0x21] = 0x60000030 +600001e7 NVC0_COMPUTE.GRAPH.SCRATCH[0x22] = 0x600001e7 +40000030 NVC0_COMPUTE.GRAPH.SCRATCH[0x23] = 0x40000030 +00701c24 NVC0_COMPUTE.GRAPH.SCRATCH[0x24] = 0x701c24 +49c00000 NVC0_COMPUTE.GRAPH.SCRATCH[0x25] = 0x49c00000 +0000dc04 NVC0_COMPUTE.GRAPH.SCRATCH[0x26] = 0xdc04 +2c000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x27] = 0x2c000000 +00001c03 NVC0_COMPUTE.GRAPH.SCRATCH[0x28] = 0x1c03 +78000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x29] = 0x78000000 +0c01dc03 NVC0_COMPUTE.GRAPH.SCRATCH[0x2a] = 0xc01dc03 +1a8e0000 NVC0_COMPUTE.GRAPH.SCRATCH[0x2b] = 0x1a8e0000 +c00001e7 NVC0_COMPUTE.GRAPH.SCRATCH[0x2c] = 0xc00001e7 +4000002f NVC0_COMPUTE.GRAPH.SCRATCH[0x2d] = 0x4000002f +40101c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x2e] = 0x40101c85 +c0000003 NVC0_COMPUTE.GRAPH.SCRATCH[0x2f] = 0xc0000003 +00000007 NVC0_COMPUTE.GRAPH.SCRATCH[0x30] = 0x7 +6000002d NVC0_COMPUTE.GRAPH.SCRATCH[0x31] = 0x6000002d +c001dc03 NVC0_COMPUTE.GRAPH.SCRATCH[0x32] = 0xc001dc03 +188e4405 NVC0_COMPUTE.GRAPH.SCRATCH[0x33] = 0x188e4405 +400001e7 NVC0_COMPUTE.GRAPH.SCRATCH[0x34] = 0x400001e7 +40000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x35] = 0x40000000 +fc029de4 NVC0_COMPUTE.GRAPH.SCRATCH[0x36] = 0xfc029de4 +28000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x37] = 0x28000000 +fc02ddf4 NVC0_COMPUTE.GRAPH.SCRATCH[0x38] = 0xfc02ddf4 +28000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x39] = 0x28000000 +80109c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x3a] = 0x80109c85 +c0000002 NVC0_COMPUTE.GRAPH.SCRATCH[0x3b] = 0xc0000002 +3010dc85 NVC0_COMPUTE.GRAPH.SCRATCH[0x3c] = 0x3010dc85 +c0000001 NVC0_COMPUTE.GRAPH.SCRATCH[0x3d] = 0xc0000001 +10115c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x3e] = 0x10115c85 +c0000002 NVC0_COMPUTE.GRAPH.SCRATCH[0x3f] = 0xc0000002 +40000007 NVC0_COMPUTE.GRAPH.SCRATCH[0x40] = 0x40000007 +60000003 NVC0_COMPUTE.GRAPH.SCRATCH[0x41] = 0x60000003 +90201f85 NVC0_COMPUTE.GRAPH.SCRATCH[0x42] = 0x90201f85 +84000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x43] = 0x84000000 +00109c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x44] = 0x109c85 +c0000001 NVC0_COMPUTE.GRAPH.SCRATCH[0x45] = 0xc0000001 +30101c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x46] = 0x30101c85 +c8000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x47] = 0xc8000000 +00201c03 NVC0_COMPUTE.GRAPH.SCRATCH[0x48] = 0x201c03 +4801c001 NVC0_COMPUTE.GRAPH.SCRATCH[0x49] = 0x4801c001 +0000dc02 NVC0_COMPUTE.GRAPH.SCRATCH[0x4a] = 0xdc02 +3bfc0000 NVC0_COMPUTE.GRAPH.SCRATCH[0x4b] = 0x3bfc0000 +17f01c43 NVC0_COMPUTE.GRAPH.SCRATCH[0x4c] = 0x17f01c43 +48000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x4d] = 0x48000000 +00211c03 NVC0_COMPUTE.GRAPH.SCRATCH[0x4e] = 0x211c03 +4801c001 NVC0_COMPUTE.GRAPH.SCRATCH[0x4f] = 0x4801c001 +0031dc03 NVC0_COMPUTE.GRAPH.SCRATCH[0x50] = 0x31dc03 +190e4000 NVC0_COMPUTE.GRAPH.SCRATCH[0x51] = 0x190e4000 +fc03dc03 NVC0_COMPUTE.GRAPH.SCRATCH[0x52] = 0xfc03dc03 +190e0000 NVC0_COMPUTE.GRAPH.SCRATCH[0x53] = 0x190e0000 +fc501c43 NVC0_COMPUTE.GRAPH.SCRATCH[0x54] = 0xfc501c43 +48000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x55] = 0x48000000 +c0111c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x56] = 0xc0111c85 +c8000001 NVC0_COMPUTE.GRAPH.SCRATCH[0x57] = 0xc8000001 +0401dc04 NVC0_COMPUTE.GRAPH.SCRATCH[0x58] = 0x401dc04 +0c0e0000 NVC0_COMPUTE.GRAPH.SCRATCH[0x59] = 0xc0e0000 +d0101c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x5a] = 0xd0101c85 +c8000001 NVC0_COMPUTE.GRAPH.SCRATCH[0x5b] = 0xc8000001 +a00001e7 NVC0_COMPUTE.GRAPH.SCRATCH[0x5c] = 0xa00001e7 +40000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x5d] = 0x40000000 +00109c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x5e] = 0x109c85 +c0000001 NVC0_COMPUTE.GRAPH.SCRATCH[0x5f] = 0xc0000001 +1010dc85 NVC0_COMPUTE.GRAPH.SCRATCH[0x60] = 0x1010dc85 +c0000002 NVC0_COMPUTE.GRAPH.SCRATCH[0x61] = 0xc0000002 +04001de2 NVC0_COMPUTE.GRAPH.SCRATCH[0x62] = 0x4001de2 +18000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x63] = 0x18000000 +00201c05 NVC0_COMPUTE.GRAPH.SCRATCH[0x64] = 0x201c05 +14000001 NVC0_COMPUTE.GRAPH.SCRATCH[0x65] = 0x14000001 +c0001de7 NVC0_COMPUTE.GRAPH.SCRATCH[0x66] = 0xc0001de7 +40000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x67] = 0x40000000 +00109c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x68] = 0x109c85 +c0000001 NVC0_COMPUTE.GRAPH.SCRATCH[0x69] = 0xc0000001 +1010dc85 NVC0_COMPUTE.GRAPH.SCRATCH[0x6a] = 0x1010dc85 +c0000002 NVC0_COMPUTE.GRAPH.SCRATCH[0x6b] = 0xc0000002 +00201c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x6c] = 0x201c85 +a0000001 NVC0_COMPUTE.GRAPH.SCRATCH[0x6d] = 0xa0000001 +04000003 NVC0_COMPUTE.GRAPH.SCRATCH[0x6e] = 0x4000003 +4800c000 NVC0_COMPUTE.GRAPH.SCRATCH[0x6f] = 0x4800c000 +00200085 NVC0_COMPUTE.GRAPH.SCRATCH[0x70] = 0x200085 +e8000001 NVC0_COMPUTE.GRAPH.SCRATCH[0x71] = 0xe8000001 +400021e7 NVC0_COMPUTE.GRAPH.SCRATCH[0x72] = 0x400021e7 +4003ffff NVC0_COMPUTE.GRAPH.SCRATCH[0x73] = 0x4003ffff +00001df4 NVC0_COMPUTE.GRAPH.SCRATCH[0x74] = 0x1df4 +40000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x75] = 0x40000000 +80101c85 NVC0_COMPUTE.GRAPH.SCRATCH[0x76] = 0x80101c85 +c0000003 NVC0_COMPUTE.GRAPH.SCRATCH[0x77] = 0xc0000003 +14009c03 NVC0_COMPUTE.GRAPH.SCRATCH[0x78] = 0x14009c03 +4800c000 NVC0_COMPUTE.GRAPH.SCRATCH[0x79] = 0x4800c000 +c021dc03 NVC0_COMPUTE.GRAPH.SCRATCH[0x7a] = 0xc021dc03 +198e4405 NVC0_COMPUTE.GRAPH.SCRATCH[0x7b] = 0x198e4405 +600001e7 NVC0_COMPUTE.GRAPH.SCRATCH[0x7c] = 0x600001e7 +40000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x7d] = 0x40000000 +fc011de4 NVC0_COMPUTE.GRAPH.SCRATCH[0x7e] = 0xfc011de4 +28000000 NVC0_COMPUTE.GRAPH.SCRATCH[0x7f] = 0x28000000 +fc015de4 NVC0_COMPUTE.0x3600 = 0xfc015de4 +28000000 NVC0_COMPUTE.0x3604 = 0x28000000 +c0001de7 NVC0_COMPUTE.0x3608 = 0xc0001de7 +40000012 NVC0_COMPUTE.0x360c = 0x40000012 +fc001de4 NVC0_COMPUTE.0x3610 = 0xfc001de4 +28000000 NVC0_COMPUTE.0x3614 = 0x28000000 +80000007 NVC0_COMPUTE.0x3618 = 0x80000007 +68000012 NVC0_COMPUTE.0x361c = 0x68000012 +c0101c85 NVC0_COMPUTE.0x3620 = 0xc0101c85 +c8000000 NVC0_COMPUTE.0x3624 = 0xc8000000 +80111c85 NVC0_COMPUTE.0x3628 = 0x80111c85 +c0000002 NVC0_COMPUTE.0x362c = 0xc0000002 +30115c85 NVC0_COMPUTE.0x3630 = 0x30115c85 +c0000001 NVC0_COMPUTE.0x3634 = 0xc0000001 +b0401f85 NVC0_COMPUTE.0x3638 = 0xb0401f85 +84000000 NVC0_COMPUTE.0x363c = 0x84000000 +20101c85 NVC0_COMPUTE.0x3640 = 0x20101c85 +c8000000 NVC0_COMPUTE.0x3644 = 0xc8000000 +2000dc03 NVC0_COMPUTE.0x3648 = 0x2000dc03 +6000c000 NVC0_COMPUTE.0x364c = 0x6000c000 +fc3fdd03 NVC0_COMPUTE.0x3650 = 0xfc3fdd03 +48010000 NVC0_COMPUTE.0x3654 = 0x48010000 +60001c03 NVC0_COMPUTE.0x3658 = 0x60001c03 +5800c000 NVC0_COMPUTE.0x365c = 0x5800c000 +6010dc85 NVC0_COMPUTE.0x3660 = 0x6010dc85 +c8000003 NVC0_COMPUTE.0x3664 = 0xc8000003 +fc01dc43 NVC0_COMPUTE.0x3668 = 0xfc01dc43 +1a8e0000 NVC0_COMPUTE.0x366c = 0x1a8e0000 +70101c85 NVC0_COMPUTE.0x3670 = 0x70101c85 +c8000003 NVC0_COMPUTE.0x3674 = 0xc8000003 +400021e7 NVC0_COMPUTE.0x3678 = 0x400021e7 +40000003 NVC0_COMPUTE.0x367c = 0x40000003 +60111ca5 NVC0_COMPUTE.0x3680 = 0x60111ca5 +c0000003 NVC0_COMPUTE.0x3684 = 0xc0000003 +00401f45 NVC0_COMPUTE.0x3688 = 0x401f45 +84000000 NVC0_COMPUTE.0x368c = 0x84000000 +0c03dc23 NVC0_COMPUTE.0x3690 = 0xc03dc23 +1a8ec16b NVC0_COMPUTE.0x3694 = 0x1a8ec16b +c00005e7 NVC0_COMPUTE.0x3698 = 0xc00005e7 +40000002 NVC0_COMPUTE.0x369c = 0x40000002 +70101c85 NVC0_COMPUTE.0x36a0 = 0x70101c85 +c0000003 NVC0_COMPUTE.0x36a4 = 0xc0000003 +08019de4 NVC0_COMPUTE.0x36a8 = 0x8019de4 +28000000 NVC0_COMPUTE.0x36ac = 0x28000000 +0401dde2 NVC0_COMPUTE.0x36b0 = 0x401dde2 +18000000 NVC0_COMPUTE.0x36b4 = 0x18000000 +00015de4 NVC0_COMPUTE.0x36b8 = 0x15de4 +28000000 NVC0_COMPUTE.0x36bc = 0x28000000 +60101c85 NVC0_COMPUTE.0x36c0 = 0x60101c85 +c0000003 NVC0_COMPUTE.0x36c4 = 0xc0000003 +00011de4 NVC0_COMPUTE.0x36c8 = 0x11de4 +28000000 NVC0_COMPUTE.0x36cc = 0x28000000 +00010007 NVC0_COMPUTE.0x36d0 = 0x10007 +100001fc NVC0_COMPUTE.0x36d4 = 0x100001fc +fc4fdd03 NVC0_COMPUTE.0x36d8 = 0xfc4fdd03 +48010000 NVC0_COMPUTE.0x36dc = 0x48010000 +fc51dc43 NVC0_COMPUTE.0x36e0 = 0xfc51dc43 +190e0000 NVC0_COMPUTE.0x36e4 = 0x190e0000 +000021e7 NVC0_COMPUTE.0x36e8 = 0x21e7 +a8000000 NVC0_COMPUTE.0x36ec = 0xa8000000 +60111ea5 NVC0_COMPUTE.0x36f0 = 0x60111ea5 +c0000003 NVC0_COMPUTE.0x36f4 = 0xc0000003 +30401f85 NVC0_COMPUTE.0x36f8 = 0x30401f85 +84000000 NVC0_COMPUTE.0x36fc = 0x84000000 +20011c03 NVC0_COMPUTE.0x3700 = 0x20011c03 +6000c000 NVC0_COMPUTE.0x3704 = 0x6000c000 +60015c03 NVC0_COMPUTE.0x3708 = 0x60015c03 +5800c000 NVC0_COMPUTE.0x370c = 0x5800c000 +fc4fdd03 NVC0_COMPUTE.0x3710 = 0xfc4fdd03 +48010000 NVC0_COMPUTE.0x3714 = 0x48010000 +60111ca5 NVC0_COMPUTE.0x3718 = 0x60111ca5 +c8000003 NVC0_COMPUTE.0x371c = 0xc8000003 +fc51dc43 NVC0_COMPUTE.0x3720 = 0xfc51dc43 +1a8e0000 NVC0_COMPUTE.0x3724 = 0x1a8e0000 +800021e7 NVC0_COMPUTE.0x3728 = 0x800021e7 +40000000 NVC0_COMPUTE.0x372c = 0x40000000 +60111ca5 NVC0_COMPUTE.0x3730 = 0x60111ca5 +c0000003 NVC0_COMPUTE.0x3734 = 0xc0000003 +00401f45 NVC0_COMPUTE.0x3738 = 0x401f45 +84000000 NVC0_COMPUTE.0x373c = 0x84000000 +0c03dc23 NVC0_COMPUTE.0x3740 = 0xc03dc23 +190ec16b NVC0_COMPUTE.0x3744 = 0x190ec16b +400005e7 NVC0_COMPUTE.0x3748 = 0x400005e7 +4003fffd NVC0_COMPUTE.0x374c = 0x4003fffd +a0000007 NVC0_COMPUTE.0x3750 = 0xa0000007 +6000000c NVC0_COMPUTE.0x3754 = 0x6000000c +600001e7 NVC0_COMPUTE.0x3758 = 0x600001e7 +4000000c NVC0_COMPUTE.0x375c = 0x4000000c +00701c24 NVC0_COMPUTE.0x3760 = 0x701c24 +49c00000 NVC0_COMPUTE.0x3764 = 0x49c00000 +0000dc04 NVC0_COMPUTE.0x3768 = 0xdc04 +2c000000 NVC0_COMPUTE.0x376c = 0x2c000000 +00001c03 NVC0_COMPUTE.0x3770 = 0x1c03 +78000000 NVC0_COMPUTE.0x3774 = 0x78000000 +0c01dc03 NVC0_COMPUTE.0x3778 = 0xc01dc03 +1a8e0000 NVC0_COMPUTE.0x377c = 0x1a8e0000 +c00001e7 NVC0_COMPUTE.0x3780 = 0xc00001e7 +4000000b NVC0_COMPUTE.0x3784 = 0x4000000b +c021dc03 NVC0_COMPUTE.0x3788 = 0xc021dc03 +188e4405 NVC0_COMPUTE.0x378c = 0x188e4405 +40000007 NVC0_COMPUTE.0x3790 = 0x40000007 +60000009 NVC0_COMPUTE.0x3794 = 0x60000009 +400001e7 NVC0_COMPUTE.0x3798 = 0x400001e7 +40000000 NVC0_COMPUTE.0x379c = 0x40000000 +fc011de4 NVC0_COMPUTE.0x37a0 = 0xfc011de4 +28000000 NVC0_COMPUTE.0x37a4 = 0x28000000 +fc015df4 NVC0_COMPUTE.0x37a8 = 0xfc015df4 +28000000 NVC0_COMPUTE.0x37ac = 0x28000000 +80111c85 NVC0_COMPUTE.0x37b0 = 0x80111c85 +c0000002 NVC0_COMPUTE.0x37b4 = 0xc0000002 +30115c85 NVC0_COMPUTE.0x37b8 = 0x30115c85 +c0000001 NVC0_COMPUTE.0x37bc = 0xc0000001 +0010dc85 NVC0_COMPUTE.0x37c0 = 0x10dc85 +c0000001 NVC0_COMPUTE.0x37c4 = 0xc0000001 +10119c85 NVC0_COMPUTE.0x37c8 = 0x10119c85 +c0000002 NVC0_COMPUTE.0x37cc = 0xc0000002 +80000007 NVC0_COMPUTE.0x37d0 = 0x80000007 +60000002 NVC0_COMPUTE.0x37d4 = 0x60000002 +b0401f85 NVC0_COMPUTE.0x37d8 = 0xb0401f85 +84000000 NVC0_COMPUTE.0x37dc = 0x84000000 +1030dc03 NVC0_COMPUTE.0x37e0 = 0x1030dc03 +4801c001 NVC0_COMPUTE.0x37e4 = 0x4801c001 +00311c02 NVC0_COMPUTE.0x37e8 = 0x311c02 +3bfc0000 NVC0_COMPUTE.0x37ec = 0x3bfc0000 +1bf0dc43 NVC0_COMPUTE.0x37f0 = 0x1bf0dc43 +48000000 NVC0_COMPUTE.0x37f4 = 0x48000000 +0041dc03 NVC0_COMPUTE.0x37f8 = 0x41dc03 +190e4000 NVC0_COMPUTE.0x37fc = 0x190e4000 +fc33dc03 NVC0_COMPUTE.GRAPH.MACRO[0] = 0xfc33dc03 +190e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0] = 0x190e0000 +0401dc04 NVC0_COMPUTE.GRAPH.MACRO[0x1] = 0x401dc04 +0c0e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x1] = 0xc0e0000 +a00001e7 NVC0_COMPUTE.GRAPH.MACRO[0x2] = 0xa00001e7 +40000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x2] = 0x40000000 +00111c85 NVC0_COMPUTE.GRAPH.MACRO[0x3] = 0x111c85 +c0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x3] = 0xc0000001 +10115c85 NVC0_COMPUTE.GRAPH.MACRO[0x4] = 0x10115c85 +c0000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x4] = 0xc0000002 +0400dde2 NVC0_COMPUTE.GRAPH.MACRO[0x5] = 0x400dde2 +18000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x5] = 0x18000000 +1040dc05 NVC0_COMPUTE.GRAPH.MACRO[0x6] = 0x1040dc05 +14000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x6] = 0x14000001 +c0001de7 NVC0_COMPUTE.GRAPH.MACRO[0x7] = 0xc0001de7 +40000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x7] = 0x40000000 +00111c85 NVC0_COMPUTE.GRAPH.MACRO[0x8] = 0x111c85 +c0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x8] = 0xc0000001 +10115c85 NVC0_COMPUTE.GRAPH.MACRO[0x9] = 0x10115c85 +c0000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x9] = 0xc0000002 +1040dc85 NVC0_COMPUTE.GRAPH.MACRO[0xa] = 0x1040dc85 +a0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0xa] = 0xa0000001 +0430c003 NVC0_COMPUTE.GRAPH.MACRO[0xb] = 0x430c003 +4800c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0xb] = 0x4800c000 +1040c085 NVC0_COMPUTE.GRAPH.MACRO[0xc] = 0x1040c085 +e8000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0xc] = 0xe8000001 +400021e7 NVC0_COMPUTE.GRAPH.MACRO[0xd] = 0x400021e7 +4003ffff NVC0_COMPUTE.GRAPH.MACRO_PARAM[0xd] = 0x4003ffff +00001df4 NVC0_COMPUTE.GRAPH.MACRO[0xe] = 0x1df4 +40000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0xe] = 0x40000000 +0010dc85 NVC0_COMPUTE.GRAPH.MACRO[0xf] = 0x10dc85 +c0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0xf] = 0xc0000001 +10115c85 NVC0_COMPUTE.GRAPH.MACRO[0x10] = 0x10115c85 +c0000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x10] = 0xc0000002 +60000007 NVC0_COMPUTE.GRAPH.MACRO[0x11] = 0x60000007 +60000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x11] = 0x60000002 +1030dc03 NVC0_COMPUTE.GRAPH.MACRO[0x12] = 0x1030dc03 +4801c001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x12] = 0x4801c001 +00311c02 NVC0_COMPUTE.GRAPH.MACRO[0x13] = 0x311c02 +3bfc0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x13] = 0x3bfc0000 +17f0dc43 NVC0_COMPUTE.GRAPH.MACRO[0x14] = 0x17f0dc43 +48000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x14] = 0x48000000 +0041dc03 NVC0_COMPUTE.GRAPH.MACRO[0x15] = 0x41dc03 +190e4000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x15] = 0x190e4000 +fc33dc03 NVC0_COMPUTE.GRAPH.MACRO[0x16] = 0xfc33dc03 +190e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x16] = 0x190e0000 +0401dc04 NVC0_COMPUTE.GRAPH.MACRO[0x17] = 0x401dc04 +0c0e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x17] = 0xc0e0000 +a00001e7 NVC0_COMPUTE.GRAPH.MACRO[0x18] = 0xa00001e7 +40000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x18] = 0x40000000 +00111c85 NVC0_COMPUTE.GRAPH.MACRO[0x19] = 0x111c85 +c0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x19] = 0xc0000001 +10115c85 NVC0_COMPUTE.GRAPH.MACRO[0x1a] = 0x10115c85 +c0000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x1a] = 0xc0000002 +fc00dde2 NVC0_COMPUTE.GRAPH.MACRO[0x1b] = 0xfc00dde2 +1bffffff NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x1b] = 0x1bffffff +1040dc05 NVC0_COMPUTE.GRAPH.MACRO[0x1c] = 0x1040dc05 +14000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x1c] = 0x14000001 +c0001de7 NVC0_COMPUTE.GRAPH.MACRO[0x1d] = 0xc0001de7 +40000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x1d] = 0x40000000 +00111c85 NVC0_COMPUTE.GRAPH.MACRO[0x1e] = 0x111c85 +c0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x1e] = 0xc0000001 +10115c85 NVC0_COMPUTE.GRAPH.MACRO[0x1f] = 0x10115c85 +c0000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x1f] = 0xc0000002 +1040dc85 NVC0_COMPUTE.GRAPH.MACRO[0x20] = 0x1040dc85 +a0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x20] = 0xa0000001 +fc30c003 NVC0_COMPUTE.GRAPH.MACRO[0x21] = 0xfc30c003 +4800ffff NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x21] = 0x4800ffff +1040c085 NVC0_COMPUTE.GRAPH.MACRO[0x22] = 0x1040c085 +e8000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x22] = 0xe8000001 +400021e7 NVC0_COMPUTE.GRAPH.MACRO[0x23] = 0x400021e7 +4003ffff NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x23] = 0x4003ffff +fc00ddf4 NVC0_COMPUTE.GRAPH.MACRO[0x24] = 0xfc00ddf4 +28000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x24] = 0x28000000 +c0000007 NVC0_COMPUTE.GRAPH.MACRO[0x25] = 0xc0000007 +68000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x25] = 0x68000002 +00111c85 NVC0_COMPUTE.GRAPH.MACRO[0x26] = 0x111c85 +c0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x26] = 0xc0000001 +10115c85 NVC0_COMPUTE.GRAPH.MACRO[0x27] = 0x10115c85 +c0000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x27] = 0xc0000002 +10411f85 NVC0_COMPUTE.GRAPH.MACRO[0x28] = 0x10411f85 +84000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x28] = 0x84000001 +fc41dc03 NVC0_COMPUTE.GRAPH.MACRO[0x29] = 0xfc41dc03 +190e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x29] = 0x190e0000 +c00001e7 NVC0_COMPUTE.GRAPH.MACRO[0x2a] = 0xc00001e7 +40000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x2a] = 0x40000001 +3c31dc23 NVC0_COMPUTE.GRAPH.MACRO[0x2b] = 0x3c31dc23 +1a0ec30d NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x2b] = 0x1a0ec30d +0430dc03 NVC0_COMPUTE.GRAPH.MACRO[0x2c] = 0x430dc03 +4800c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x2c] = 0x4800c000 +600001e7 NVC0_COMPUTE.GRAPH.MACRO[0x2d] = 0x600001e7 +40000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x2d] = 0x40000001 +80111c85 NVC0_COMPUTE.GRAPH.MACRO[0x2e] = 0x80111c85 +c0000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x2e] = 0xc0000002 +30115c85 NVC0_COMPUTE.GRAPH.MACRO[0x2f] = 0x30115c85 +c0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x2f] = 0xc0000001 +b0411f85 NVC0_COMPUTE.GRAPH.MACRO[0x30] = 0xb0411f85 +84000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x30] = 0x84000000 +0041dc03 NVC0_COMPUTE.GRAPH.MACRO[0x31] = 0x41dc03 +190e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x31] = 0x190e0000 +600001e7 NVC0_COMPUTE.GRAPH.MACRO[0x32] = 0x600001e7 +4003fffe NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x32] = 0x4003fffe +80111c85 NVC0_COMPUTE.GRAPH.MACRO[0x33] = 0x80111c85 +c0000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x33] = 0xc0000002 +30115c85 NVC0_COMPUTE.GRAPH.MACRO[0x34] = 0x30115c85 +c0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x34] = 0xc0000001 +b0401f85 NVC0_COMPUTE.GRAPH.MACRO[0x35] = 0xb0401f85 +84000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x35] = 0x84000000 +20011c03 NVC0_COMPUTE.GRAPH.MACRO[0x36] = 0x20011c03 +6000c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x36] = 0x6000c000 +60015c03 NVC0_COMPUTE.GRAPH.MACRO[0x37] = 0x60015c03 +5800c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x37] = 0x5800c000 +00001de7 NVC0_COMPUTE.GRAPH.MACRO[0x38] = 0x1de7 +a8000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x38] = 0xa8000000 +fc011de4 NVC0_COMPUTE.GRAPH.MACRO[0x39] = 0xfc011de4 +28000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x39] = 0x28000000 +fc015de4 NVC0_COMPUTE.GRAPH.MACRO[0x3a] = 0xfc015de4 +28000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x3a] = 0x28000000 +00001de7 NVC0_COMPUTE.GRAPH.MACRO[0x3b] = 0x1de7 +a8000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x3b] = 0xa8000000 +00001df4 NVC0_COMPUTE.GRAPH.MACRO[0x3c] = 0x1df4 +40000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x3c] = 0x40000000 +fc4fdd03 NVC0_COMPUTE.GRAPH.MACRO[0x3d] = 0xfc4fdd03 +48010000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x3d] = 0x48010000 +fc51dc43 NVC0_COMPUTE.GRAPH.MACRO[0x3e] = 0xfc51dc43 +1a8e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x3e] = 0x1a8e0000 +200001e7 NVC0_COMPUTE.GRAPH.MACRO[0x3f] = 0x200001e7 +40000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x3f] = 0x40000001 +80111c85 NVC0_COMPUTE.GRAPH.MACRO[0x40] = 0x80111c85 +c0000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x40] = 0xc0000002 +30115c85 NVC0_COMPUTE.GRAPH.MACRO[0x41] = 0x30115c85 +c0000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x41] = 0xc0000001 +2010de85 NVC0_COMPUTE.GRAPH.MACRO[0x42] = 0x2010de85 +c0000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x42] = 0xc0000000 +b0401f85 NVC0_COMPUTE.GRAPH.MACRO[0x43] = 0xb0401f85 +84000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x43] = 0x84000000 +0c01dc03 NVC0_COMPUTE.GRAPH.MACRO[0x44] = 0xc01dc03 +1a8e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x44] = 0x1a8e0000 +200001e7 NVC0_COMPUTE.GRAPH.MACRO[0x45] = 0x200001e7 +40000001 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x45] = 0x40000001 +fc011de4 NVC0_COMPUTE.GRAPH.MACRO[0x46] = 0xfc011de4 +28000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x46] = 0x28000000 +fc015de4 NVC0_COMPUTE.GRAPH.MACRO[0x47] = 0xfc015de4 +28000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x47] = 0x28000000 +00001de7 NVC0_COMPUTE.GRAPH.MACRO[0x48] = 0x1de7 +a8000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x48] = 0xa8000000 +08019de4 NVC0_COMPUTE.GRAPH.MACRO[0x49] = 0x8019de4 +28000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x49] = 0x28000000 +0401dde2 NVC0_COMPUTE.GRAPH.MACRO[0x4a] = 0x401dde2 +18000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x4a] = 0x18000000 +00010007 NVC0_COMPUTE.GRAPH.MACRO[0x4b] = 0x10007 +100001fc NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x4b] = 0x100001fc +fc4fdd03 NVC0_COMPUTE.GRAPH.MACRO[0x4c] = 0xfc4fdd03 +48010000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x4c] = 0x48010000 +fc51dc43 NVC0_COMPUTE.GRAPH.MACRO[0x4d] = 0xfc51dc43 +190e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x4d] = 0x190e0000 +000021e7 NVC0_COMPUTE.GRAPH.MACRO[0x4e] = 0x21e7 +a8000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x4e] = 0xa8000000 +00001df4 NVC0_COMPUTE.GRAPH.MACRO[0x4f] = 0x1df4 +40000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x4f] = 0x40000000 +c0101e85 NVC0_COMPUTE.GRAPH.MACRO[0x50] = 0xc0101e85 +c0000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x50] = 0xc0000000 +04001c03 NVC0_COMPUTE.GRAPH.MACRO[0x51] = 0x4001c03 +4800c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x51] = 0x4800c000 +4001dc23 NVC0_COMPUTE.GRAPH.MACRO[0x52] = 0x4001dc23 +1a8ec30d NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x52] = 0x1a8ec30d +c0101c85 NVC0_COMPUTE.GRAPH.MACRO[0x53] = 0xc0101c85 +c8000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x53] = 0xc8000000 +000001e7 NVC0_COMPUTE.GRAPH.MACRO[0x54] = 0x1e7 +4003ffee NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x54] = 0x4003ffee +fc011de4 NVC0_COMPUTE.GRAPH.MACRO[0x55] = 0xfc011de4 +28000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x55] = 0x28000000 +fc015de4 NVC0_COMPUTE.GRAPH.MACRO[0x56] = 0xfc015de4 +28000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x56] = 0x28000000 +00001de7 NVC0_COMPUTE.GRAPH.MACRO[0x57] = 0x1de7 +a8000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x57] = 0xa8000000 +fc4fdd03 NVC0_COMPUTE.GRAPH.MACRO[0x58] = 0xfc4fdd03 +48010000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x58] = 0x48010000 +fc51dc43 NVC0_COMPUTE.GRAPH.MACRO[0x59] = 0xfc51dc43 +190e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x59] = 0x190e0000 +400001e7 NVC0_COMPUTE.GRAPH.MACRO[0x5a] = 0x400001e7 +40000010 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x5a] = 0x40000010 +40429c03 NVC0_COMPUTE.GRAPH.MACRO[0x5b] = 0x40429c03 +4801c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x5b] = 0x4801c000 +fca01c03 NVC0_COMPUTE.GRAPH.MACRO[0x5c] = 0xfca01c03 +6800c003 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x5c] = 0x6800c003 +03f0dc04 NVC0_COMPUTE.GRAPH.MACRO[0x5d] = 0x3f0dc04 +3000c3c0 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x5d] = 0x3000c3c0 +fc0fdd03 NVC0_COMPUTE.GRAPH.MACRO[0x5e] = 0xfc0fdd03 +48010000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x5e] = 0x48010000 +fff1dc43 NVC0_COMPUTE.GRAPH.MACRO[0x5f] = 0xfff1dc43 +190e0000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x5f] = 0x190e0000 +00301c04 NVC0_COMPUTE.GRAPH.MACRO[0x60] = 0x301c04 +3400c3c0 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x60] = 0x3400c3c0 +fc52dc43 NVC0_COMPUTE.GRAPH.MACRO[0x61] = 0xfc52dc43 +48000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x61] = 0x48000000 +000081e7 NVC0_COMPUTE.GRAPH.MACRO[0x62] = 0x81e7 +40000002 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x62] = 0x40000002 +c0a323c5 NVC0_COMPUTE.GRAPH.MACRO[0x63] = 0xc0a323c5 +87ffffff NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x63] = 0x87ffffff +c010e003 NVC0_COMPUTE.GRAPH.MACRO[0x64] = 0xc010e003 +4800c003 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x64] = 0x4800c003 +10322003 NVC0_COMPUTE.GRAPH.MACRO[0x65] = 0x10322003 +48014000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x65] = 0x48014000 +fff26043 NVC0_COMPUTE.GRAPH.MACRO[0x66] = 0xfff26043 +48000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x66] = 0x48000000 +00002203 NVC0_COMPUTE.GRAPH.MACRO[0x67] = 0x2203 +4801c004 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x67] = 0x4801c004 +10002003 NVC0_COMPUTE.GRAPH.MACRO[0x68] = 0x10002003 +5800c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x68] = 0x5800c000 +fff0e143 NVC0_COMPUTE.GRAPH.MACRO[0x69] = 0xfff0e143 +48000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x69] = 0x48000000 +00302383 NVC0_COMPUTE.GRAPH.MACRO[0x6a] = 0x302383 +40000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x6a] = 0x40000000 +1030e003 NVC0_COMPUTE.GRAPH.MACRO[0x6b] = 0x1030e003 +5800c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x6b] = 0x5800c000 +4002a003 NVC0_COMPUTE.GRAPH.MACRO[0x6c] = 0x4002a003 +2015c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x6c] = 0x2015c000 +008323c5 NVC0_COMPUTE.GRAPH.MACRO[0x6d] = 0x8323c5 +94000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x6d] = 0x94000000 +008123c5 NVC0_COMPUTE.GRAPH.MACRO[0x6e] = 0x8123c5 +84000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x6e] = 0x84000000 +70022003 NVC0_COMPUTE.GRAPH.MACRO[0x6f] = 0x70022003 +5800c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x6f] = 0x5800c000 +2030e083 NVC0_COMPUTE.GRAPH.MACRO[0x70] = 0x2030e083 +40000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x70] = 0x40000000 +0cb2e043 NVC0_COMPUTE.GRAPH.MACRO[0x71] = 0xcb2e043 +48000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x71] = 0x48000000 +c0a123c5 NVC0_COMPUTE.GRAPH.MACRO[0x72] = 0xc0a123c5 +97ffffff NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x72] = 0x97ffffff +0c00dde2 NVC0_COMPUTE.GRAPH.MACRO[0x73] = 0xc00dde2 +1800016b NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x73] = 0x1800016b +40111ca5 NVC0_COMPUTE.GRAPH.MACRO[0x74] = 0x40111ca5 +c0000003 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x74] = 0xc0000003 +00a0df45 NVC0_COMPUTE.GRAPH.MACRO[0x75] = 0xa0df45 +94000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x75] = 0x94000000 +00a01f85 NVC0_COMPUTE.GRAPH.MACRO[0x76] = 0xa01f85 +84000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x76] = 0x84000000 +fc411c03 NVC0_COMPUTE.GRAPH.MACRO[0x77] = 0xfc411c03 +6800c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x77] = 0x6800c000 +fc00dc03 NVC0_COMPUTE.GRAPH.MACRO[0x78] = 0xfc00dc03 +6800fbff NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x78] = 0x6800fbff +00a0df85 NVC0_COMPUTE.GRAPH.MACRO[0x79] = 0xa0df85 +94000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x79] = 0x94000000 +00a01f85 NVC0_COMPUTE.GRAPH.MACRO[0x7a] = 0xa01f85 +84000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x7a] = 0x84000000 +4440dc03 NVC0_COMPUTE.GRAPH.MACRO[0x7b] = 0x4440dc03 +6000c000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x7b] = 0x6000c000 +e0511c86 NVC0_COMPUTE.GRAPH.MACRO[0x7c] = 0xe0511c86 +14000400 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x7c] = 0x14000400 +f0015de2 NVC0_COMPUTE.GRAPH.MACRO[0x7d] = 0xf0015de2 +18000294 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x7d] = 0x18000294 +fc001c02 NVC0_COMPUTE.GRAPH.MACRO[0x7e] = 0xfc001c02 +3bfe07ff NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x7e] = 0x3bfe07ff +0c00dc43 NVC0_COMPUTE.GRAPH.MACRO[0x7f] = 0xc00dc43 +68000000 NVC0_COMPUTE.GRAPH.MACRO_PARAM[0x7f] = 0x68000000 +00a0df85 NVC0_COMPUTE.0x3c00 = 0xa0df85 +94000000 NVC0_COMPUTE.0x3c04 = 0x94000000 +00a01f85 NVC0_COMPUTE.0x3c08 = 0xa01f85 +84000000 NVC0_COMPUTE.0x3c0c = 0x84000000 +fc40dc03 NVC0_COMPUTE.0x3c10 = 0xfc40dc03 +4800ffff NVC0_COMPUTE.0x3c14 = 0x4800ffff +08011de2 NVC0_COMPUTE.0x3c18 = 0x8011de2 +18000000 NVC0_COMPUTE.0x3c1c = 0x18000000 +0c40dc03 NVC0_COMPUTE.0x3c20 = 0xc40dc03 +60000000 NVC0_COMPUTE.0x3c24 = 0x60000000 +20a11c03 NVC0_COMPUTE.0x3c28 = 0x20a11c03 +5800c000 NVC0_COMPUTE.0x3c2c = 0x5800c000 +fc30dc03 NVC0_COMPUTE.0x3c30 = 0xfc30dc03 +4800ffff NVC0_COMPUTE.0x3c34 = 0x4800ffff +10b25f03 NVC0_COMPUTE.0x3c38 = 0x10b25f03 +40000000 NVC0_COMPUTE.0x3c3c = 0x40000000 +10a0df85 NVC0_COMPUTE.0x3c40 = 0x10a0df85 +94000000 NVC0_COMPUTE.0x3c44 = 0x94000000 +fc00dde4 NVC0_COMPUTE.0x3c48 = 0xfc00dde4 +28000000 NVC0_COMPUTE.0x3c4c = 0x28000000 +7010dc85 NVC0_COMPUTE.0x3c50 = 0x7010dc85 +c8000003 NVC0_COMPUTE.0x3c54 = 0xc8000003 +fc001c02 NVC0_COMPUTE.0x3c58 = 0xfc001c02 +3801ffff NVC0_COMPUTE.0x3c5c = 0x3801ffff +00a01f85 NVC0_COMPUTE.0x3c60 = 0xa01f85 +94000000 NVC0_COMPUTE.0x3c64 = 0x94000000 +20a15f85 NVC0_COMPUTE.0x3c68 = 0x20a15f85 +94000000 NVC0_COMPUTE.0x3c6c = 0x94000000 +80109c85 NVC0_COMPUTE.0x3c70 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x3c74 = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x3c78 = 0x3010dc85 +c0000001 NVC0_COMPUTE.0x3c7c = 0xc0000001 +e0101c85 NVC0_COMPUTE.0x3c80 = 0xe0101c85 +c0000001 NVC0_COMPUTE.0x3c84 = 0xc0000001 +f0119c85 NVC0_COMPUTE.0x3c88 = 0xf0119c85 +c0000001 NVC0_COMPUTE.0x3c8c = 0xc0000001 +fc01dde4 NVC0_COMPUTE.0x3c90 = 0xfc01dde4 +28000000 NVC0_COMPUTE.0x3c94 = 0x28000000 +a0000007 NVC0_COMPUTE.0x3c98 = 0xa0000007 +60000003 NVC0_COMPUTE.0x3c9c = 0x60000003 +80211fa5 NVC0_COMPUTE.0x3ca0 = 0x80211fa5 +84000000 NVC0_COMPUTE.0x3ca4 = 0x84000000 +00001c02 NVC0_COMPUTE.0x3ca8 = 0x1c02 +3bfc0000 NVC0_COMPUTE.0x3cac = 0x3bfc0000 +fc63dc03 NVC0_COMPUTE.0x3cb0 = 0xfc63dc03 +190e0000 NVC0_COMPUTE.0x3cb4 = 0x190e0000 +0001dc03 NVC0_COMPUTE.0x3cb8 = 0x1dc03 +190e4000 NVC0_COMPUTE.0x3cbc = 0x190e4000 +0401dc04 NVC0_COMPUTE.0x3cc0 = 0x401dc04 +0c0e0000 NVC0_COMPUTE.0x3cc4 = 0xc0e0000 +14019de4 NVC0_COMPUTE.0x3cc8 = 0x14019de4 +28000000 NVC0_COMPUTE.0x3ccc = 0x28000000 +f8401c03 NVC0_COMPUTE.0x3cd0 = 0xf8401c03 +6800ffff NVC0_COMPUTE.0x3cd4 = 0x6800ffff +30a19f85 NVC0_COMPUTE.0x3cd8 = 0x30a19f85 +94000000 NVC0_COMPUTE.0x3cdc = 0x94000000 +f8021c03 NVC0_COMPUTE.0x3ce0 = 0xf8021c03 +6800ffff NVC0_COMPUTE.0x3ce4 = 0x6800ffff +a00001e7 NVC0_COMPUTE.0x3ce8 = 0xa00001e7 +40000000 NVC0_COMPUTE.0x3cec = 0x40000000 +e0109ca5 NVC0_COMPUTE.0x3cf0 = 0xe0109ca5 +c0000001 NVC0_COMPUTE.0x3cf4 = 0xc0000001 +00211f25 NVC0_COMPUTE.0x3cf8 = 0x211f25 +54103000 NVC0_COMPUTE.0x3cfc = 0x54103000 +b011dc85 NVC0_COMPUTE.0x3d00 = 0xb011dc85 +c8000001 NVC0_COMPUTE.0x3d04 = 0xc8000001 +00201ca5 NVC0_COMPUTE.0x3d08 = 0x201ca5 +9c000000 NVC0_COMPUTE.0x3d0c = 0x9c000000 +a0001de7 NVC0_COMPUTE.0x3d10 = 0xa0001de7 +40000001 NVC0_COMPUTE.0x3d14 = 0x40000001 +e0109ca5 NVC0_COMPUTE.0x3d18 = 0xe0109ca5 +c0000001 NVC0_COMPUTE.0x3d1c = 0xc0000001 +1cf3dc04 NVC0_COMPUTE.0x3d20 = 0x1cf3dc04 +0c0e0000 NVC0_COMPUTE.0x3d24 = 0xc0e0000 +b011de85 NVC0_COMPUTE.0x3d28 = 0xb011de85 +c0000001 NVC0_COMPUTE.0x3d2c = 0xc0000001 +00219c85 NVC0_COMPUTE.0x3d30 = 0x219c85 +a0000000 NVC0_COMPUTE.0x3d34 = 0xa0000000 +1021c185 NVC0_COMPUTE.0x3d38 = 0x1021c185 +a0000000 NVC0_COMPUTE.0x3d3c = 0xa0000000 +106fc503 NVC0_COMPUTE.0x3d40 = 0x106fc503 +48010000 NVC0_COMPUTE.0x3d44 = 0x48010000 +b011dc85 NVC0_COMPUTE.0x3d48 = 0xb011dc85 +c8000001 NVC0_COMPUTE.0x3d4c = 0xc8000001 +1475c443 NVC0_COMPUTE.0x3d50 = 0x1475c443 +190e0000 NVC0_COMPUTE.0x3d54 = 0x190e0000 +1c91c404 NVC0_COMPUTE.0x3d58 = 0x1c91c404 +20040000 NVC0_COMPUTE.0x3d5c = 0x20040000 +18800404 NVC0_COMPUTE.0x3d60 = 0x18800404 +20040000 NVC0_COMPUTE.0x3d64 = 0x20040000 +1021c485 NVC0_COMPUTE.0x3d68 = 0x1021c485 +e8000000 NVC0_COMPUTE.0x3d6c = 0xe8000000 +00200085 NVC0_COMPUTE.0x3d70 = 0x200085 +e8000000 NVC0_COMPUTE.0x3d74 = 0xe8000000 +600025e7 NVC0_COMPUTE.0x3d78 = 0x600025e7 +4003fffe NVC0_COMPUTE.0x3d7c = 0x4003fffe +00001df4 NVC0_COMPUTE.0x3d80 = 0x1df4 +40000000 NVC0_COMPUTE.0x3d84 = 0x40000000 +b0101c85 NVC0_COMPUTE.0x3d88 = 0xb0101c85 +c0000001 NVC0_COMPUTE.0x3d8c = 0xc0000001 +184fdd03 NVC0_COMPUTE.0x3d90 = 0x184fdd03 +48010000 NVC0_COMPUTE.0x3d94 = 0x48010000 +0051dc43 NVC0_COMPUTE.0x3d98 = 0x51dc43 +1a8e0000 NVC0_COMPUTE.0x3d9c = 0x1a8e0000 +000001e7 NVC0_COMPUTE.0x3da0 = 0x1e7 +40000002 NVC0_COMPUTE.0x3da4 = 0x40000002 +c0111ea5 NVC0_COMPUTE.0x3da8 = 0xc0111ea5 +c0000001 NVC0_COMPUTE.0x3dac = 0xc0000001 +a0000007 NVC0_COMPUTE.0x3db0 = 0xa0000007 +60000001 NVC0_COMPUTE.0x3db4 = 0x60000001 +00401c02 NVC0_COMPUTE.0x3db8 = 0x401c02 +3bfc0000 NVC0_COMPUTE.0x3dbc = 0x3bfc0000 +fc53dc03 NVC0_COMPUTE.0x3dc0 = 0xfc53dc03 +190e0000 NVC0_COMPUTE.0x3dc4 = 0x190e0000 +0001dc03 NVC0_COMPUTE.0x3dc8 = 0x1dc03 +190e4000 NVC0_COMPUTE.0x3dcc = 0x190e4000 +0401dc04 NVC0_COMPUTE.0x3dd0 = 0x401dc04 +0c0e0000 NVC0_COMPUTE.0x3dd4 = 0xc0e0000 +600001e7 NVC0_COMPUTE.0x3dd8 = 0x600001e7 +40000000 NVC0_COMPUTE.0x3ddc = 0x40000000 +fc001de2 NVC0_COMPUTE.0x3de0 = 0xfc001de2 +1bffffff NVC0_COMPUTE.0x3de4 = 0x1bffffff +00401c05 NVC0_COMPUTE.0x3de8 = 0x401c05 +14000000 NVC0_COMPUTE.0x3dec = 0x14000000 +80001de7 NVC0_COMPUTE.0x3df0 = 0x80001de7 +40000000 NVC0_COMPUTE.0x3df4 = 0x40000000 +00401c85 NVC0_COMPUTE.0x3df8 = 0x401c85 +a0000000 NVC0_COMPUTE.0x3dfc = 0xa0000000 +fc000003 NVC0_COMPUTE.0x3e00 = 0xfc000003 +4800ffff NVC0_COMPUTE.0x3e04 = 0x4800ffff +00400085 NVC0_COMPUTE.0x3e08 = 0x400085 +e8000000 NVC0_COMPUTE.0x3e0c = 0xe8000000 +800021e7 NVC0_COMPUTE.0x3e10 = 0x800021e7 +4003ffff NVC0_COMPUTE.0x3e14 = 0x4003ffff +00001df4 NVC0_COMPUTE.0x3e18 = 0x1df4 +40000000 NVC0_COMPUTE.0x3e1c = 0x40000000 +00001df4 NVC0_COMPUTE.0x3e20 = 0x1df4 +40000000 NVC0_COMPUTE.0x3e24 = 0x40000000 +70101e85 NVC0_COMPUTE.0x3e28 = 0x70101e85 +c0000003 NVC0_COMPUTE.0x3e2c = 0xc0000003 +04001c03 NVC0_COMPUTE.0x3e30 = 0x4001c03 +4800c000 NVC0_COMPUTE.0x3e34 = 0x4800c000 +4001dc23 NVC0_COMPUTE.0x3e38 = 0x4001dc23 +1a8ec30d NVC0_COMPUTE.0x3e3c = 0x1a8ec30d +70101c85 NVC0_COMPUTE.0x3e40 = 0x70101c85 +c8000003 NVC0_COMPUTE.0x3e44 = 0xc8000003 +800001e7 NVC0_COMPUTE.0x3e48 = 0x800001e7 +4003fff8 NVC0_COMPUTE.0x3e4c = 0x4003fff8 +2c015de4 NVC0_COMPUTE.0x3e50 = 0x2c015de4 +28000000 NVC0_COMPUTE.0x3e54 = 0x28000000 +28011de4 NVC0_COMPUTE.0x3e58 = 0x28011de4 +28000000 NVC0_COMPUTE.0x3e5c = 0x28000000 +00010007 NVC0_COMPUTE.0x3e60 = 0x10007 +100001d0 NVC0_COMPUTE.0x3e64 = 0x100001d0 +c0111ea5 NVC0_COMPUTE.0x3e68 = 0xc0111ea5 +c0000001 NVC0_COMPUTE.0x3e6c = 0xc0000001 +a0000007 NVC0_COMPUTE.0x3e70 = 0xa0000007 +60000001 NVC0_COMPUTE.0x3e74 = 0x60000001 +00401c02 NVC0_COMPUTE.0x3e78 = 0x401c02 +3bfc0000 NVC0_COMPUTE.0x3e7c = 0x3bfc0000 +fc53dc03 NVC0_COMPUTE.0x3e80 = 0xfc53dc03 +190e0000 NVC0_COMPUTE.0x3e84 = 0x190e0000 +0001dc03 NVC0_COMPUTE.0x3e88 = 0x1dc03 +190e4000 NVC0_COMPUTE.0x3e8c = 0x190e4000 +0401dc04 NVC0_COMPUTE.0x3e90 = 0x401dc04 +0c0e0000 NVC0_COMPUTE.0x3e94 = 0xc0e0000 +600001e7 NVC0_COMPUTE.0x3e98 = 0x600001e7 +40000000 NVC0_COMPUTE.0x3e9c = 0x40000000 +fc001de2 NVC0_COMPUTE.0x3ea0 = 0xfc001de2 +1bffffff NVC0_COMPUTE.0x3ea4 = 0x1bffffff +00401c05 NVC0_COMPUTE.0x3ea8 = 0x401c05 +14000000 NVC0_COMPUTE.0x3eac = 0x14000000 +80001de7 NVC0_COMPUTE.0x3eb0 = 0x80001de7 +40000000 NVC0_COMPUTE.0x3eb4 = 0x40000000 +00401c85 NVC0_COMPUTE.0x3eb8 = 0x401c85 +a0000000 NVC0_COMPUTE.0x3ebc = 0xa0000000 +fc000003 NVC0_COMPUTE.0x3ec0 = 0xfc000003 +4800ffff NVC0_COMPUTE.0x3ec4 = 0x4800ffff +00400085 NVC0_COMPUTE.0x3ec8 = 0x400085 +e8000000 NVC0_COMPUTE.0x3ecc = 0xe8000000 +800021e7 NVC0_COMPUTE.0x3ed0 = 0x800021e7 +4003ffff NVC0_COMPUTE.0x3ed4 = 0x4003ffff +00001df4 NVC0_COMPUTE.0x3ed8 = 0x1df4 +40000000 NVC0_COMPUTE.0x3edc = 0x40000000 +40001de7 NVC0_COMPUTE.0x3ee0 = 0x40001de7 +40000004 NVC0_COMPUTE.0x3ee4 = 0x40000004 +c0111ea5 NVC0_COMPUTE.0x3ee8 = 0xc0111ea5 +c0000001 NVC0_COMPUTE.0x3eec = 0xc0000001 +a0000007 NVC0_COMPUTE.0x3ef0 = 0xa0000007 +60000001 NVC0_COMPUTE.0x3ef4 = 0x60000001 +00401c02 NVC0_COMPUTE.0x3ef8 = 0x401c02 +3bfc0000 NVC0_COMPUTE.0x3efc = 0x3bfc0000 +fc53dc03 NVC0_COMPUTE.0x3f00 = 0xfc53dc03 +190e0000 NVC0_COMPUTE.0x3f04 = 0x190e0000 +0001dc03 NVC0_COMPUTE.0x3f08 = 0x1dc03 +190e4000 NVC0_COMPUTE.0x3f0c = 0x190e4000 +0401dc04 NVC0_COMPUTE.0x3f10 = 0x401dc04 +0c0e0000 NVC0_COMPUTE.0x3f14 = 0xc0e0000 +600001e7 NVC0_COMPUTE.0x3f18 = 0x600001e7 +40000000 NVC0_COMPUTE.0x3f1c = 0x40000000 +fc001de2 NVC0_COMPUTE.0x3f20 = 0xfc001de2 +1bffffff NVC0_COMPUTE.0x3f24 = 0x1bffffff +00401c05 NVC0_COMPUTE.0x3f28 = 0x401c05 +14000000 NVC0_COMPUTE.0x3f2c = 0x14000000 +80001de7 NVC0_COMPUTE.0x3f30 = 0x80001de7 +40000000 NVC0_COMPUTE.0x3f34 = 0x40000000 +00401c85 NVC0_COMPUTE.0x3f38 = 0x401c85 +a0000000 NVC0_COMPUTE.0x3f3c = 0xa0000000 +fc000003 NVC0_COMPUTE.0x3f40 = 0xfc000003 +4800ffff NVC0_COMPUTE.0x3f44 = 0x4800ffff +00400085 NVC0_COMPUTE.0x3f48 = 0x400085 +e8000000 NVC0_COMPUTE.0x3f4c = 0xe8000000 +800021e7 NVC0_COMPUTE.0x3f50 = 0x800021e7 +4003ffff NVC0_COMPUTE.0x3f54 = 0x4003ffff +fc001df4 NVC0_COMPUTE.0x3f58 = 0xfc001df4 +28000000 NVC0_COMPUTE.0x3f5c = 0x28000000 +00109c85 NVC0_COMPUTE.0x3f60 = 0x109c85 +c0000001 NVC0_COMPUTE.0x3f64 = 0xc0000001 +1010dc85 NVC0_COMPUTE.0x3f68 = 0x1010dc85 +c0000002 NVC0_COMPUTE.0x3f6c = 0xc0000002 +0020df85 NVC0_COMPUTE.0x3f70 = 0x20df85 +84000001 NVC0_COMPUTE.0x3f74 = 0x84000001 +fc31dc03 NVC0_COMPUTE.0x3f78 = 0xfc31dc03 +190e0000 NVC0_COMPUTE.0x3f7c = 0x190e0000 +c00001e7 NVC0_COMPUTE.0x3f80 = 0xc00001e7 +40000001 NVC0_COMPUTE.0x3f84 = 0x40000001 +3c01dc23 NVC0_COMPUTE.0x3f88 = 0x3c01dc23 +1a0ec30d NVC0_COMPUTE.0x3f8c = 0x1a0ec30d +04001c03 NVC0_COMPUTE.0x3f90 = 0x4001c03 +4800c000 NVC0_COMPUTE.0x3f94 = 0x4800c000 +600001e7 NVC0_COMPUTE.0x3f98 = 0x600001e7 +40000001 NVC0_COMPUTE.0x3f9c = 0x40000001 +80109c85 NVC0_COMPUTE.0x3fa0 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x3fa4 = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x3fa8 = 0x3010dc85 +c0000001 NVC0_COMPUTE.0x3fac = 0xc0000001 +9020df85 NVC0_COMPUTE.0x3fb0 = 0x9020df85 +84000000 NVC0_COMPUTE.0x3fb4 = 0x84000000 +30109c85 NVC0_COMPUTE.0x3fb8 = 0x30109c85 +c0000000 NVC0_COMPUTE.0x3fbc = 0xc0000000 +0831dc03 NVC0_COMPUTE.0x3fc0 = 0x831dc03 +190e0000 NVC0_COMPUTE.0x3fc4 = 0x190e0000 +400001e7 NVC0_COMPUTE.0x3fc8 = 0x400001e7 +4003fffe NVC0_COMPUTE.0x3fcc = 0x4003fffe +80109c85 NVC0_COMPUTE.0x3fd0 = 0x80109c85 +c0000002 NVC0_COMPUTE.0x3fd4 = 0xc0000002 +3010dc85 NVC0_COMPUTE.0x3fd8 = 0x3010dc85 +c0000001 NVC0_COMPUTE.0x3fdc = 0xc0000001 +90201f85 NVC0_COMPUTE.0x3fe0 = 0x90201f85 +84000000 NVC0_COMPUTE.0x3fe4 = 0x84000000 +20029c03 NVC0_COMPUTE.0x3fe8 = 0x20029c03 +6000c000 NVC0_COMPUTE.0x3fec = 0x6000c000 +6002dc13 NVC0_COMPUTE.0x3ff0 = 0x6002dc13 +5800c000 NVC0_COMPUTE.0x3ff4 = 0x5800c000 +fc029de4 NVC0_COMPUTE.0x3ff8 = 0xfc029de4 +28000000 NVC0_COMPUTE.0x3ffc = 0x28000000 +fc02ddf4 NVC0_COMPUTE.0x4000 = 0xfc02ddf4 +28000000 NVC0_COMPUTE.0x4004 = 0x28000000 +fcafdd03 size 7343, subchannel 6 (0x0), offset 0x740c, increment +48010000 OBJ0.0x740c +fcb1dc43 OBJ0.0x7410 +1a8e0000 OBJ0.0x7414 +200001e7 OBJ0.0x7418 +40000001 OBJ0.0x741c +80111c85 OBJ0.0x7420 +c0000002 OBJ0.0x7424 +30115c85 OBJ0.0x7428 +c0000001 OBJ0.0x742c +4010de85 OBJ0.0x7430 +c0000000 OBJ0.0x7434 +90401f85 OBJ0.0x7438 +84000000 OBJ0.0x743c +0c01dc03 OBJ0.0x7440 +1a8e0000 OBJ0.0x7444 +600001e7 OBJ0.0x7448 +40000001 OBJ0.0x744c +fc011de4 OBJ0.0x7450 +28000000 OBJ0.0x7454 +fc015de4 OBJ0.0x7458 +28000000 OBJ0.0x745c +00001de7 OBJ0.0x7460 +a8000000 OBJ0.0x7464 +40119c85 OBJ0.0x7468 +c0000003 OBJ0.0x746c +2c015de4 OBJ0.0x7470 +28000000 OBJ0.0x7474 +28011de4 OBJ0.0x7478 +28000000 OBJ0.0x747c +0401dde2 OBJ0.0x7480 +18000000 OBJ0.0x7484 +00010007 OBJ0.0x7488 +100001fc OBJ0.0x748c +fc4fdd03 OBJ0.0x7490 +48010000 OBJ0.0x7494 +fc51dc43 OBJ0.0x7498 +190e0000 OBJ0.0x749c +000021e7 OBJ0.0x74a0 +a8000000 OBJ0.0x74a4 +00001df4 OBJ0.0x74a8 +40000000 OBJ0.0x74ac +f0101e85 OBJ0.0x74b0 +c0000000 OBJ0.0x74b4 +04001c03 OBJ0.0x74b8 +4800c000 OBJ0.0x74bc +4001dc23 OBJ0.0x74c0 +1a8ec30d OBJ0.0x74c4 +f0101c85 OBJ0.0x74c8 +c8000000 OBJ0.0x74cc +e00001e7 OBJ0.0x74d0 +4003ffc9 OBJ0.0x74d4 +fc011de4 OBJ0.0x74d8 +28000000 OBJ0.0x74dc +fc015de4 OBJ0.0x74e0 +28000000 OBJ0.0x74e4 +00001de7 OBJ0.0x74e8 +a8000000 OBJ0.0x74ec +fc4fdd03 OBJ0.0x74f0 +48010000 OBJ0.0x74f4 +fc51dc43 OBJ0.0x74f8 +190e0000 OBJ0.0x74fc +000001e7 OBJ0.0x7500 +40000010 OBJ0.0x7504 +40431c03 OBJ0.0x7508 +4801c000 OBJ0.0x750c +fcc01c03 OBJ0.0x7510 +6800c003 OBJ0.0x7514 +03f0dc04 OBJ0.0x7518 +3000c3c0 OBJ0.0x751c +fc0fdd03 OBJ0.0x7520 +48010000 OBJ0.0x7524 +fff1dc43 OBJ0.0x7528 +190e0000 OBJ0.0x752c +00301c04 OBJ0.0x7530 +3400c3c0 OBJ0.0x7534 +fc535c43 OBJ0.0x7538 +48000000 OBJ0.0x753c +000081e7 OBJ0.0x7540 +40000002 OBJ0.0x7544 +c0c223c5 OBJ0.0x7548 +87ffffff OBJ0.0x754c +0010e003 OBJ0.0x7550 +4800c004 OBJ0.0x7554 +1033a003 OBJ0.0x7558 +48014000 OBJ0.0x755c +fff3e043 OBJ0.0x7560 +48000000 OBJ0.0x7564 +00002203 OBJ0.0x7568 +4801c004 OBJ0.0x756c +1000e003 OBJ0.0x7570 +5800c000 OBJ0.0x7574 +fff02143 OBJ0.0x7578 +48000000 OBJ0.0x757c +0c00e383 OBJ0.0x7580 +40000000 OBJ0.0x7584 +10002003 OBJ0.0x7588 +5800c000 OBJ0.0x758c +40332003 OBJ0.0x7590 +2019c000 OBJ0.0x7594 +00e223c5 OBJ0.0x7598 +94000000 OBJ0.0x759c +00e123c5 OBJ0.0x75a0 +84000000 OBJ0.0x75a4 +70322003 OBJ0.0x75a8 +5800c000 OBJ0.0x75ac +20002083 OBJ0.0x75b0 +40000000 OBJ0.0x75b4 +00d36043 OBJ0.0x75b8 +48000000 OBJ0.0x75bc +c0c123c5 OBJ0.0x75c0 +97ffffff OBJ0.0x75c4 +0c00dde2 OBJ0.0x75c8 +1800016b OBJ0.0x75cc +70111c85 OBJ0.0x75d0 +c0000000 OBJ0.0x75d4 +50115c85 OBJ0.0x75d8 +c0000003 OBJ0.0x75dc +00c0df45 OBJ0.0x75e0 +94000000 OBJ0.0x75e4 +00c01f85 OBJ0.0x75e8 +84000000 OBJ0.0x75ec +f001dde2 OBJ0.0x75f0 +18000294 OBJ0.0x75f4 +20c19c03 OBJ0.0x75f8 +5800c000 OBJ0.0x75fc +fc411c03 OBJ0.0x7600 +6800c000 OBJ0.0x7604 +18d2df03 OBJ0.0x7608 +40000000 OBJ0.0x760c +fc00dc03 OBJ0.0x7610 +6800fbff OBJ0.0x7614 +00c0df85 OBJ0.0x7618 +94000000 OBJ0.0x761c +00c01f85 OBJ0.0x7620 +84000000 OBJ0.0x7624 +4440dc03 OBJ0.0x7628 +6000c000 OBJ0.0x762c +d0511c86 OBJ0.0x7630 +14000400 OBJ0.0x7634 +fc001c02 OBJ0.0x7638 +3bfe07ff OBJ0.0x763c +0c00dc43 OBJ0.0x7640 +68000000 OBJ0.0x7644 +00c0df85 OBJ0.0x7648 +94000000 OBJ0.0x764c +00c01f85 OBJ0.0x7650 +84000000 OBJ0.0x7654 +fc40dc03 OBJ0.0x7658 +4800ffff OBJ0.0x765c +08011de2 OBJ0.0x7660 +18000000 OBJ0.0x7664 +0c40dc03 OBJ0.0x7668 +60000000 OBJ0.0x766c +40111ca5 OBJ0.0x7670 +c0000002 OBJ0.0x7674 +fc30dc03 OBJ0.0x7678 +4800ffff OBJ0.0x767c +10c0df85 OBJ0.0x7680 +94000000 OBJ0.0x7684 +fc00dde4 OBJ0.0x7688 +28000000 OBJ0.0x768c +7010dc85 OBJ0.0x7690 +c8000003 OBJ0.0x7694 +fc001c02 OBJ0.0x7698 +3801ffff OBJ0.0x769c +00c01f85 OBJ0.0x76a0 +94000000 OBJ0.0x76a4 +20c1df85 OBJ0.0x76a8 +94000000 OBJ0.0x76ac +80109c85 OBJ0.0x76b0 +c0000002 OBJ0.0x76b4 +3010dc85 OBJ0.0x76b8 +c0000001 OBJ0.0x76bc +00401c02 OBJ0.0x76c0 +3bfc0000 OBJ0.0x76c4 +fc53dc03 OBJ0.0x76c8 +190e0000 OBJ0.0x76cc +fc01dde4 OBJ0.0x76d0 +28000000 OBJ0.0x76d4 +0001dc03 OBJ0.0x76d8 +190e4000 OBJ0.0x76dc +00000007 OBJ0.0x76e0 +60000003 OBJ0.0x76e4 +60221fa5 OBJ0.0x76e8 +84000000 OBJ0.0x76ec +0401dc04 OBJ0.0x76f0 +0c0e0000 OBJ0.0x76f4 +24019de4 OBJ0.0x76f8 +28000000 OBJ0.0x76fc +f8801c03 OBJ0.0x7700 +6800ffff OBJ0.0x7704 +30c19f85 OBJ0.0x7708 +94000000 OBJ0.0x770c +f8029c03 OBJ0.0x7710 +6800ffff OBJ0.0x7714 +800001e7 OBJ0.0x7718 +40000000 OBJ0.0x771c +00421f25 OBJ0.0x7720 +54143000 OBJ0.0x7724 +a011dc85 OBJ0.0x7728 +c8000001 OBJ0.0x772c +00401ca5 OBJ0.0x7730 +9c000000 OBJ0.0x7734 +80001de7 OBJ0.0x7738 +40000001 OBJ0.0x773c +00419c85 OBJ0.0x7740 +a0000000 OBJ0.0x7744 +1cf3dc04 OBJ0.0x7748 +0c0e0000 OBJ0.0x774c +a011de85 OBJ0.0x7750 +c0000001 OBJ0.0x7754 +1041c185 OBJ0.0x7758 +a0000000 OBJ0.0x775c +206fc503 OBJ0.0x7760 +48010000 OBJ0.0x7764 +a011dc85 OBJ0.0x7768 +c8000001 OBJ0.0x776c +2475c443 OBJ0.0x7770 +190e0000 OBJ0.0x7774 +1cb1c404 OBJ0.0x7778 +20040000 OBJ0.0x777c +18a00404 OBJ0.0x7780 +20040000 OBJ0.0x7784 +1041c485 OBJ0.0x7788 +e8000000 OBJ0.0x778c +00400085 OBJ0.0x7790 +e8000000 OBJ0.0x7794 +800025e7 OBJ0.0x7798 +4003fffe OBJ0.0x779c +00001df4 OBJ0.0x77a0 +40000000 OBJ0.0x77a4 +a0101c85 OBJ0.0x77a8 +c0000001 OBJ0.0x77ac +188fdd03 OBJ0.0x77b0 +48010000 OBJ0.0x77b4 +0091dc43 OBJ0.0x77b8 +1a8e0000 OBJ0.0x77bc +000001e7 OBJ0.0x77c0 +40000002 OBJ0.0x77c4 +20111ea5 OBJ0.0x77c8 +c0000002 OBJ0.0x77cc +a0000007 OBJ0.0x77d0 +60000001 OBJ0.0x77d4 +00401c02 OBJ0.0x77d8 +3bfc0000 OBJ0.0x77dc +fc53dc03 OBJ0.0x77e0 +190e0000 OBJ0.0x77e4 +0001dc03 OBJ0.0x77e8 +190e4000 OBJ0.0x77ec +0401dc04 OBJ0.0x77f0 +0c0e0000 OBJ0.0x77f4 +600001e7 OBJ0.0x77f8 +40000000 OBJ0.0x77fc +fc001de2 OBJ0.0x7800 +1bffffff OBJ0.0x7804 +00401c05 OBJ0.0x7808 +14000000 OBJ0.0x780c +80001de7 OBJ0.0x7810 +40000000 OBJ0.0x7814 +00401c85 OBJ0.0x7818 +a0000000 OBJ0.0x781c +fc000003 OBJ0.0x7820 +4800ffff OBJ0.0x7824 +00400085 OBJ0.0x7828 +e8000000 OBJ0.0x782c +800021e7 OBJ0.0x7830 +4003ffff OBJ0.0x7834 +00001df4 OBJ0.0x7838 +40000000 OBJ0.0x783c +00001df4 OBJ0.0x7840 +40000000 OBJ0.0x7844 +70101e85 OBJ0.0x7848 +c0000003 OBJ0.0x784c +04001c03 OBJ0.0x7850 +4800c000 OBJ0.0x7854 +4001dc23 OBJ0.0x7858 +1a8ec30d OBJ0.0x785c +70101c85 OBJ0.0x7860 +c8000003 OBJ0.0x7864 +000001e7 OBJ0.0x7868 +4003fff9 OBJ0.0x786c +34015de4 OBJ0.0x7870 +28000000 OBJ0.0x7874 +30011de4 OBJ0.0x7878 +28000000 OBJ0.0x787c +00010007 OBJ0.0x7880 +100001d0 OBJ0.0x7884 +20111ea5 OBJ0.0x7888 +c0000002 OBJ0.0x788c +a0000007 OBJ0.0x7890 +60000001 OBJ0.0x7894 +00401c02 OBJ0.0x7898 +3bfc0000 OBJ0.0x789c +fc53dc03 OBJ0.0x78a0 +190e0000 OBJ0.0x78a4 +0001dc03 OBJ0.0x78a8 +190e4000 OBJ0.0x78ac +0401dc04 OBJ0.0x78b0 +0c0e0000 OBJ0.0x78b4 +600001e7 OBJ0.0x78b8 +40000000 OBJ0.0x78bc +fc001de2 OBJ0.0x78c0 +1bffffff OBJ0.0x78c4 +00401c05 OBJ0.0x78c8 +14000000 OBJ0.0x78cc +80001de7 OBJ0.0x78d0 +40000000 OBJ0.0x78d4 +00401c85 OBJ0.0x78d8 +a0000000 OBJ0.0x78dc +fc000003 OBJ0.0x78e0 +4800ffff OBJ0.0x78e4 +00400085 OBJ0.0x78e8 +e8000000 OBJ0.0x78ec +800021e7 OBJ0.0x78f0 +4003ffff OBJ0.0x78f4 +00001df4 OBJ0.0x78f8 +40000000 OBJ0.0x78fc +60001de7 OBJ0.0x7900 +40000004 OBJ0.0x7904 +20111ea5 OBJ0.0x7908 +c0000002 OBJ0.0x790c +a0000007 OBJ0.0x7910 +60000001 OBJ0.0x7914 +00401c02 OBJ0.0x7918 +3bfc0000 OBJ0.0x791c +fc53dc03 OBJ0.0x7920 +190e0000 OBJ0.0x7924 +0001dc03 OBJ0.0x7928 +190e4000 OBJ0.0x792c +0401dc04 OBJ0.0x7930 +0c0e0000 OBJ0.0x7934 +600001e7 OBJ0.0x7938 +40000000 OBJ0.0x793c +fc001de2 OBJ0.0x7940 +1bffffff OBJ0.0x7944 +00401c05 OBJ0.0x7948 +14000000 OBJ0.0x794c +80001de7 OBJ0.0x7950 +40000000 OBJ0.0x7954 +00401c85 OBJ0.0x7958 +a0000000 OBJ0.0x795c +fc000003 OBJ0.0x7960 +4800ffff OBJ0.0x7964 +00400085 OBJ0.0x7968 +e8000000 OBJ0.0x796c +800021e7 OBJ0.0x7970 +4003ffff OBJ0.0x7974 +00001df4 OBJ0.0x7978 +40000000 OBJ0.0x797c +5010de85 OBJ0.0x7980 +c0000000 OBJ0.0x7984 +fc001de4 OBJ0.0x7988 +28000000 OBJ0.0x798c +00111c85 OBJ0.0x7990 +200348e0 OBJ0.0x7994 +00010000 OBJ0.0x7998 +00000001 OBJ0.0x799c +0000a400 OBJ0.0x79a0 +200148e3 OBJ0.0x79a4 +000000fc OBJ0.0x79a8 +652948e4 OBJ0.0x79ac +c0000001 OBJ0.0x79b0 +10115c85 OBJ0.0x79b4 +c0000002 OBJ0.0x79b8 +f0411f85 OBJ0.0x79bc +84000000 OBJ0.0x79c0 +fc41dc03 OBJ0.0x79c4 +190e0000 OBJ0.0x79c8 +a00001e7 OBJ0.0x79cc +40000001 OBJ0.0x79d0 +3c01dc23 OBJ0.0x79d4 +1a0ec30d OBJ0.0x79d8 +04001c03 OBJ0.0x79dc +4800c000 OBJ0.0x79e0 +400001e7 OBJ0.0x79e4 +40000001 OBJ0.0x79e8 +80111c85 OBJ0.0x79ec +c0000002 OBJ0.0x79f0 +30115c85 OBJ0.0x79f4 +c0000001 OBJ0.0x79f8 +70411f85 OBJ0.0x79fc +84000000 OBJ0.0x7a00 +0c41dc03 OBJ0.0x7a04 +190e0000 OBJ0.0x7a08 +600001e7 OBJ0.0x7a0c +4003fffe OBJ0.0x7a10 +80109c85 OBJ0.0x7a14 +c0000002 OBJ0.0x7a18 +3010dc85 OBJ0.0x7a1c +c0000001 OBJ0.0x7a20 +70201f85 OBJ0.0x7a24 +84000000 OBJ0.0x7a28 +20031c03 OBJ0.0x7a2c +6000c000 OBJ0.0x7a30 +60035c13 OBJ0.0x7a34 +5800c000 OBJ0.0x7a38 +fc031de4 OBJ0.0x7a3c +28000000 OBJ0.0x7a40 +fc035df4 OBJ0.0x7a44 +28000000 OBJ0.0x7a48 +fccfdd03 OBJ0.0x7a4c +48010000 OBJ0.0x7a50 +fcd1dc43 OBJ0.0x7a54 +1a8e0000 OBJ0.0x7a58 +200001e7 OBJ0.0x7a5c +40000001 OBJ0.0x7a60 +80111c85 OBJ0.0x7a64 +c0000002 OBJ0.0x7a68 +30115c85 OBJ0.0x7a6c +c0000001 OBJ0.0x7a70 +6010de85 OBJ0.0x7a74 +c0000000 OBJ0.0x7a78 +70401f85 OBJ0.0x7a7c +84000000 OBJ0.0x7a80 +0c01dc03 OBJ0.0x7a84 +1a8e0000 OBJ0.0x7a88 +600001e7 OBJ0.0x7a8c +40000001 OBJ0.0x7a90 +fc011de4 OBJ0.0x7a94 +28000000 OBJ0.0x7a98 +fc015de4 OBJ0.0x7a9c +28000000 OBJ0.0x7aa0 +00001de7 OBJ0.0x7aa4 +a8000000 OBJ0.0x7aa8 +70119c85 OBJ0.0x7aac +c0000000 OBJ0.0x7ab0 +34015de4 OBJ0.0x7ab4 +28000000 OBJ0.0x7ab8 +30011de4 OBJ0.0x7abc +28000000 OBJ0.0x7ac0 +0401dde2 OBJ0.0x7ac4 +18000000 OBJ0.0x7ac8 +00010007 OBJ0.0x7acc +100001fc OBJ0.0x7ad0 +fc4fdd03 OBJ0.0x7ad4 +48010000 OBJ0.0x7ad8 +fc51dc43 OBJ0.0x7adc +190e0000 OBJ0.0x7ae0 +000021e7 OBJ0.0x7ae4 +a8000000 OBJ0.0x7ae8 +00001df4 OBJ0.0x7aec +40000000 OBJ0.0x7af0 +10101e85 OBJ0.0x7af4 +c0000001 OBJ0.0x7af8 +04001c03 OBJ0.0x7afc +4800c000 OBJ0.0x7b00 +4001dc23 OBJ0.0x7b04 +1a8ec30d OBJ0.0x7b08 +10101c85 OBJ0.0x7b0c +c8000001 OBJ0.0x7b10 +000001e7 OBJ0.0x7b14 +4003ffa5 OBJ0.0x7b18 +fc011de4 OBJ0.0x7b1c +28000000 OBJ0.0x7b20 +fc015de4 OBJ0.0x7b24 +28000000 OBJ0.0x7b28 +00001de7 OBJ0.0x7b2c +a8000000 OBJ0.0x7b30 +fc4fdd03 OBJ0.0x7b34 +48010000 OBJ0.0x7b38 +fc51dc43 OBJ0.0x7b3c +190e0000 OBJ0.0x7b40 +000001e7 OBJ0.0x7b44 +40000010 OBJ0.0x7b48 +40431c03 OBJ0.0x7b4c +4801c000 OBJ0.0x7b50 +fcc01c03 OBJ0.0x7b54 +6800c003 OBJ0.0x7b58 +03f0dc04 OBJ0.0x7b5c +3000c3c0 OBJ0.0x7b60 +fc0fdd03 OBJ0.0x7b64 +48010000 OBJ0.0x7b68 +fff1dc43 OBJ0.0x7b6c +190e0000 OBJ0.0x7b70 +00301c04 OBJ0.0x7b74 +3400c3c0 OBJ0.0x7b78 +fc535c43 OBJ0.0x7b7c +48000000 OBJ0.0x7b80 +000081e7 OBJ0.0x7b84 +40000002 OBJ0.0x7b88 +c0c223c5 OBJ0.0x7b8c +87ffffff OBJ0.0x7b90 +4010e003 OBJ0.0x7b94 +4800c004 OBJ0.0x7b98 +1033a003 OBJ0.0x7b9c +48014000 OBJ0.0x7ba0 +fff3e043 OBJ0.0x7ba4 +48000000 OBJ0.0x7ba8 +00002203 OBJ0.0x7bac +4801c004 OBJ0.0x7bb0 +1000e003 OBJ0.0x7bb4 +5800c000 OBJ0.0x7bb8 +fff02143 OBJ0.0x7bbc +48000000 OBJ0.0x7bc0 +0c00e383 OBJ0.0x7bc4 +40000000 OBJ0.0x7bc8 +10002003 OBJ0.0x7bcc +5800c000 OBJ0.0x7bd0 +40332003 OBJ0.0x7bd4 +2019c000 OBJ0.0x7bd8 +00e223c5 OBJ0.0x7bdc +94000000 OBJ0.0x7be0 +00e123c5 OBJ0.0x7be4 +84000000 OBJ0.0x7be8 +70322003 OBJ0.0x7bec +5800c000 OBJ0.0x7bf0 +20002083 OBJ0.0x7bf4 +40000000 OBJ0.0x7bf8 +00d36043 OBJ0.0x7bfc +48000000 OBJ0.0x7c00 +c0c123c5 OBJ0.0x7c04 +97ffffff OBJ0.0x7c08 +0c00dde2 OBJ0.0x7c0c +1800016b OBJ0.0x7c10 +a0111c85 OBJ0.0x7c14 +c0000000 OBJ0.0x7c18 +50115c85 OBJ0.0x7c1c +c0000003 OBJ0.0x7c20 +00c0df45 OBJ0.0x7c24 +94000000 OBJ0.0x7c28 +00c01f85 OBJ0.0x7c2c +84000000 OBJ0.0x7c30 +f001dde2 OBJ0.0x7c34 +18000294 OBJ0.0x7c38 +20c19c03 OBJ0.0x7c3c +5800c000 OBJ0.0x7c40 +fc411c03 OBJ0.0x7c44 +6800c000 OBJ0.0x7c48 +18d2df03 OBJ0.0x7c4c +40000000 OBJ0.0x7c50 +fc00dc03 OBJ0.0x7c54 +6800fbff OBJ0.0x7c58 +00c0df85 OBJ0.0x7c5c +94000000 OBJ0.0x7c60 +00c01f85 OBJ0.0x7c64 +84000000 OBJ0.0x7c68 +4440dc03 OBJ0.0x7c6c +6000c000 OBJ0.0x7c70 +c0511c86 OBJ0.0x7c74 +14000400 OBJ0.0x7c78 +fc001c02 OBJ0.0x7c7c +3bfe07ff OBJ0.0x7c80 +0c00dc43 OBJ0.0x7c84 +68000000 OBJ0.0x7c88 +00c0df85 OBJ0.0x7c8c +94000000 OBJ0.0x7c90 +00c01f85 OBJ0.0x7c94 +84000000 OBJ0.0x7c98 +fc40dc03 OBJ0.0x7c9c +4800ffff OBJ0.0x7ca0 +08011de2 OBJ0.0x7ca4 +18000000 OBJ0.0x7ca8 +0c40dc03 OBJ0.0x7cac +60000000 OBJ0.0x7cb0 +a0111ca5 OBJ0.0x7cb4 +c0000002 OBJ0.0x7cb8 +fc30dc03 OBJ0.0x7cbc +4800ffff OBJ0.0x7cc0 +10c0df85 OBJ0.0x7cc4 +94000000 OBJ0.0x7cc8 +fc00dde4 OBJ0.0x7ccc +28000000 OBJ0.0x7cd0 +7010dc85 OBJ0.0x7cd4 +c8000003 OBJ0.0x7cd8 +fc001c02 OBJ0.0x7cdc +3801ffff OBJ0.0x7ce0 +00c01f85 OBJ0.0x7ce4 +94000000 OBJ0.0x7ce8 +20c1df85 OBJ0.0x7cec +94000000 OBJ0.0x7cf0 +80109c85 OBJ0.0x7cf4 +c0000002 OBJ0.0x7cf8 +3010dc85 OBJ0.0x7cfc +c0000001 OBJ0.0x7d00 +00401c02 OBJ0.0x7d04 +3bfc0000 OBJ0.0x7d08 +fc53dc03 OBJ0.0x7d0c +190e0000 OBJ0.0x7d10 +fc01dde4 OBJ0.0x7d14 +28000000 OBJ0.0x7d18 +0001dc03 OBJ0.0x7d1c +190e4000 OBJ0.0x7d20 +00000007 OBJ0.0x7d24 +60000003 OBJ0.0x7d28 +40221fa5 OBJ0.0x7d2c +84000000 OBJ0.0x7d30 +0401dc04 OBJ0.0x7d34 +0c0e0000 OBJ0.0x7d38 +24019de4 OBJ0.0x7d3c +28000000 OBJ0.0x7d40 +f8801c03 OBJ0.0x7d44 +6800ffff OBJ0.0x7d48 +30c19f85 OBJ0.0x7d4c +94000000 OBJ0.0x7d50 +f8029c03 OBJ0.0x7d54 +6800ffff OBJ0.0x7d58 +800001e7 OBJ0.0x7d5c +40000000 OBJ0.0x7d60 +00421f25 OBJ0.0x7d64 +54143000 OBJ0.0x7d68 +9011dc85 OBJ0.0x7d6c +c8000001 OBJ0.0x7d70 +00401ca5 OBJ0.0x7d74 +9c000000 OBJ0.0x7d78 +80001de7 OBJ0.0x7d7c +40000001 OBJ0.0x7d80 +00419c85 OBJ0.0x7d84 +a0000000 OBJ0.0x7d88 +1cf3dc04 OBJ0.0x7d8c +0c0e0000 OBJ0.0x7d90 +9011de85 OBJ0.0x7d94 +c0000001 OBJ0.0x7d98 +1041c185 OBJ0.0x7d9c +a0000000 OBJ0.0x7da0 +206fc503 OBJ0.0x7da4 +48010000 OBJ0.0x7da8 +9011dc85 OBJ0.0x7dac +c8000001 OBJ0.0x7db0 +2475c443 OBJ0.0x7db4 +190e0000 OBJ0.0x7db8 +1cb1c404 OBJ0.0x7dbc +20040000 OBJ0.0x7dc0 +18a00404 OBJ0.0x7dc4 +20040000 OBJ0.0x7dc8 +1041c485 OBJ0.0x7dcc +e8000000 OBJ0.0x7dd0 +00400085 OBJ0.0x7dd4 +e8000000 OBJ0.0x7dd8 +800025e7 OBJ0.0x7ddc +4003fffe OBJ0.0x7de0 +00001df4 OBJ0.0x7de4 +40000000 OBJ0.0x7de8 +90101c85 OBJ0.0x7dec +c0000001 OBJ0.0x7df0 +188fdd03 OBJ0.0x7df4 +48010000 OBJ0.0x7df8 +0091dc43 OBJ0.0x7dfc +1a8e0000 OBJ0.0x7e00 +000001e7 OBJ0.0x7e04 +40000002 OBJ0.0x7e08 +60111ea5 OBJ0.0x7e0c +c0000002 OBJ0.0x7e10 +a0000007 OBJ0.0x7e14 +60000001 OBJ0.0x7e18 +00401c02 OBJ0.0x7e1c +3bfc0000 OBJ0.0x7e20 +fc53dc03 OBJ0.0x7e24 +190e0000 OBJ0.0x7e28 +0001dc03 OBJ0.0x7e2c +190e4000 OBJ0.0x7e30 +0401dc04 OBJ0.0x7e34 +0c0e0000 OBJ0.0x7e38 +600001e7 OBJ0.0x7e3c +40000000 OBJ0.0x7e40 +fc001de2 OBJ0.0x7e44 +1bffffff OBJ0.0x7e48 +00401c05 OBJ0.0x7e4c +14000000 OBJ0.0x7e50 +80001de7 OBJ0.0x7e54 +40000000 OBJ0.0x7e58 +00401c85 OBJ0.0x7e5c +a0000000 OBJ0.0x7e60 +fc000003 OBJ0.0x7e64 +4800ffff OBJ0.0x7e68 +00400085 OBJ0.0x7e6c +e8000000 OBJ0.0x7e70 +800021e7 OBJ0.0x7e74 +4003ffff OBJ0.0x7e78 +00001df4 OBJ0.0x7e7c +40000000 OBJ0.0x7e80 +00001df4 OBJ0.0x7e84 +40000000 OBJ0.0x7e88 +70101e85 OBJ0.0x7e8c +c0000003 OBJ0.0x7e90 +04001c03 OBJ0.0x7e94 +4800c000 OBJ0.0x7e98 +4001dc23 OBJ0.0x7e9c +1a8ec30d OBJ0.0x7ea0 +70101c85 OBJ0.0x7ea4 +c8000003 OBJ0.0x7ea8 +000001e7 OBJ0.0x7eac +4003fff9 OBJ0.0x7eb0 +34015de4 OBJ0.0x7eb4 +28000000 OBJ0.0x7eb8 +30011de4 OBJ0.0x7ebc +28000000 OBJ0.0x7ec0 +00010007 OBJ0.0x7ec4 +100001d0 OBJ0.0x7ec8 +60111ea5 OBJ0.0x7ecc +c0000002 OBJ0.0x7ed0 +a0000007 OBJ0.0x7ed4 +60000001 OBJ0.0x7ed8 +00401c02 OBJ0.0x7edc +3bfc0000 OBJ0.0x7ee0 +fc53dc03 OBJ0.0x7ee4 +190e0000 OBJ0.0x7ee8 +0001dc03 OBJ0.0x7eec +190e4000 OBJ0.0x7ef0 +0401dc04 OBJ0.0x7ef4 +0c0e0000 OBJ0.0x7ef8 +600001e7 OBJ0.0x7efc +40000000 OBJ0.0x7f00 +fc001de2 OBJ0.0x7f04 +1bffffff OBJ0.0x7f08 +00401c05 OBJ0.0x7f0c +14000000 OBJ0.0x7f10 +80001de7 OBJ0.0x7f14 +40000000 OBJ0.0x7f18 +00401c85 OBJ0.0x7f1c +a0000000 OBJ0.0x7f20 +fc000003 OBJ0.0x7f24 +4800ffff OBJ0.0x7f28 +00400085 OBJ0.0x7f2c +e8000000 OBJ0.0x7f30 +800021e7 OBJ0.0x7f34 +4003ffff OBJ0.0x7f38 +00001df4 OBJ0.0x7f3c +40000000 OBJ0.0x7f40 +60001de7 OBJ0.0x7f44 +40000004 OBJ0.0x7f48 +60111ea5 OBJ0.0x7f4c +c0000002 OBJ0.0x7f50 +a0000007 OBJ0.0x7f54 +60000001 OBJ0.0x7f58 +00401c02 OBJ0.0x7f5c +3bfc0000 OBJ0.0x7f60 +fc53dc03 OBJ0.0x7f64 +190e0000 OBJ0.0x7f68 +0001dc03 OBJ0.0x7f6c +190e4000 OBJ0.0x7f70 +0401dc04 OBJ0.0x7f74 +0c0e0000 OBJ0.0x7f78 +600001e7 OBJ0.0x7f7c +40000000 OBJ0.0x7f80 +fc001de2 OBJ0.0x7f84 +1bffffff OBJ0.0x7f88 +00401c05 OBJ0.0x7f8c +14000000 OBJ0.0x7f90 +80001de7 OBJ0.0x7f94 +40000000 OBJ0.0x7f98 +00401c85 OBJ0.0x7f9c +a0000000 OBJ0.0x7fa0 +fc000003 OBJ0.0x7fa4 +4800ffff OBJ0.0x7fa8 +00400085 OBJ0.0x7fac +e8000000 OBJ0.0x7fb0 +800021e7 OBJ0.0x7fb4 +4003ffff OBJ0.0x7fb8 +00001df4 OBJ0.0x7fbc +40000000 OBJ0.0x7fc0 +8010de85 OBJ0.0x7fc4 +c0000000 OBJ0.0x7fc8 +fc001de4 OBJ0.0x7fcc +28000000 OBJ0.0x7fd0 +00111c85 OBJ0.0x7fd4 +c0000001 OBJ0.0x7fd8 +10115c85 OBJ0.0x7fdc +c0000002 OBJ0.0x7fe0 +e0411f85 OBJ0.0x7fe4 +84000000 OBJ0.0x7fe8 +fc41dc03 OBJ0.0x7fec +190e0000 OBJ0.0x7ff0 +a00001e7 OBJ0.0x7ff4 +40000001 OBJ0.0x7ff8 +3c01dc23 OBJ0.0x7ffc +1a0ec30d OBJ0.0x8000 +04001c03 OBJ0.0x8004 +4800c000 OBJ0.0x8008 +400001e7 OBJ0.0x800c +40000001 OBJ0.0x8010 +80111c85 OBJ0.0x8014 +c0000002 OBJ0.0x8018 +30115c85 OBJ0.0x801c +c0000001 OBJ0.0x8020 +50411f85 OBJ0.0x8024 +84000000 OBJ0.0x8028 +0c41dc03 OBJ0.0x802c +190e0000 OBJ0.0x8030 +600001e7 OBJ0.0x8034 +4003fffe OBJ0.0x8038 +80109c85 OBJ0.0x803c +c0000002 OBJ0.0x8040 +3010dc85 OBJ0.0x8044 +c0000001 OBJ0.0x8048 +50201f85 OBJ0.0x804c +84000000 OBJ0.0x8050 +20031c03 OBJ0.0x8054 +6000c000 OBJ0.0x8058 +60035c13 OBJ0.0x805c +5800c000 OBJ0.0x8060 +fc031de4 OBJ0.0x8064 +28000000 OBJ0.0x8068 +fc035df4 OBJ0.0x806c +28000000 OBJ0.0x8070 +fccfdd03 OBJ0.0x8074 +48010000 OBJ0.0x8078 +fcd1dc43 OBJ0.0x807c +1a8e0000 OBJ0.0x8080 +200001e7 OBJ0.0x8084 +40000001 OBJ0.0x8088 +80111c85 OBJ0.0x808c +c0000002 OBJ0.0x8090 +30115c85 OBJ0.0x8094 +c0000001 OBJ0.0x8098 +9010de85 OBJ0.0x809c +c0000000 OBJ0.0x80a0 +50401f85 OBJ0.0x80a4 +84000000 OBJ0.0x80a8 +0c01dc03 OBJ0.0x80ac +1a8e0000 OBJ0.0x80b0 +600001e7 OBJ0.0x80b4 +40000001 OBJ0.0x80b8 +fc011de4 OBJ0.0x80bc +28000000 OBJ0.0x80c0 +fc015de4 OBJ0.0x80c4 +28000000 OBJ0.0x80c8 +00001de7 OBJ0.0x80cc +a8000000 OBJ0.0x80d0 +a0119c85 OBJ0.0x80d4 +c0000000 OBJ0.0x80d8 +34015de4 OBJ0.0x80dc +28000000 OBJ0.0x80e0 +30011de4 OBJ0.0x80e4 +28000000 OBJ0.0x80e8 +0401dde2 OBJ0.0x80ec +18000000 OBJ0.0x80f0 +00010007 OBJ0.0x80f4 +100001fc OBJ0.0x80f8 +fc4fdd03 OBJ0.0x80fc +48010000 OBJ0.0x8100 +fc51dc43 OBJ0.0x8104 +190e0000 OBJ0.0x8108 +000021e7 OBJ0.0x810c +a8000000 OBJ0.0x8110 +00001df4 OBJ0.0x8114 +40000000 OBJ0.0x8118 +40101e85 OBJ0.0x811c +c0000001 OBJ0.0x8120 +04001c03 OBJ0.0x8124 +4800c000 OBJ0.0x8128 +4001dc23 OBJ0.0x812c +1a8ec30d OBJ0.0x8130 +40101c85 OBJ0.0x8134 +c8000001 OBJ0.0x8138 +200001e7 OBJ0.0x813c +4003ff80 OBJ0.0x8140 +fc011de4 OBJ0.0x8144 +28000000 OBJ0.0x8148 +fc015de4 OBJ0.0x814c +28000000 OBJ0.0x8150 +00001de7 OBJ0.0x8154 +a8000000 OBJ0.0x8158 +fc4fdd03 OBJ0.0x815c +48010000 OBJ0.0x8160 +fc51dc43 OBJ0.0x8164 +190e0000 OBJ0.0x8168 +000001e7 OBJ0.0x816c +40000010 OBJ0.0x8170 +40431c03 OBJ0.0x8174 +4801c000 OBJ0.0x8178 +fcc01c03 OBJ0.0x817c +6800c003 OBJ0.0x8180 +03f0dc04 OBJ0.0x8184 +3000c3c0 OBJ0.0x8188 +fc0fdd03 OBJ0.0x818c +48010000 OBJ0.0x8190 +fff1dc43 OBJ0.0x8194 +190e0000 OBJ0.0x8198 +00301c04 OBJ0.0x819c +3400c3c0 OBJ0.0x81a0 +fc535c43 OBJ0.0x81a4 +48000000 OBJ0.0x81a8 +000081e7 OBJ0.0x81ac +40000002 OBJ0.0x81b0 +c0c223c5 OBJ0.0x81b4 +87ffffff OBJ0.0x81b8 +8010e003 OBJ0.0x81bc +4800c004 OBJ0.0x81c0 +1033a003 OBJ0.0x81c4 +48014000 OBJ0.0x81c8 +fff3e043 OBJ0.0x81cc +48000000 OBJ0.0x81d0 +00002203 OBJ0.0x81d4 +4801c004 OBJ0.0x81d8 +1000e003 OBJ0.0x81dc +5800c000 OBJ0.0x81e0 +fff02143 OBJ0.0x81e4 +48000000 OBJ0.0x81e8 +0c00e383 OBJ0.0x81ec +40000000 OBJ0.0x81f0 +10002003 OBJ0.0x81f4 +5800c000 OBJ0.0x81f8 +40332003 OBJ0.0x81fc +2019c000 OBJ0.0x8200 +00e223c5 OBJ0.0x8204 +94000000 OBJ0.0x8208 +00e123c5 OBJ0.0x820c +84000000 OBJ0.0x8210 +70322003 OBJ0.0x8214 +5800c000 OBJ0.0x8218 +20002083 OBJ0.0x821c +40000000 OBJ0.0x8220 +00d36043 OBJ0.0x8224 +48000000 OBJ0.0x8228 +c0c123c5 OBJ0.0x822c +97ffffff OBJ0.0x8230 +0c00dde2 OBJ0.0x8234 +1800016b OBJ0.0x8238 +e0111c85 OBJ0.0x823c +c0000000 OBJ0.0x8240 +50115c85 OBJ0.0x8244 +c0000003 OBJ0.0x8248 +00c0df45 OBJ0.0x824c +94000000 OBJ0.0x8250 +00c01f85 OBJ0.0x8254 +84000000 OBJ0.0x8258 +f001dde2 OBJ0.0x825c +18000294 OBJ0.0x8260 +20c19c03 OBJ0.0x8264 +5800c000 OBJ0.0x8268 +fc411c03 OBJ0.0x826c +6800c000 OBJ0.0x8270 +18d2df03 OBJ0.0x8274 +40000000 OBJ0.0x8278 +fc00dc03 OBJ0.0x827c +6800fbff OBJ0.0x8280 +00c0df85 OBJ0.0x8284 +94000000 OBJ0.0x8288 +00c01f85 OBJ0.0x828c +84000000 OBJ0.0x8290 +4440dc03 OBJ0.0x8294 +6000c000 OBJ0.0x8298 +b0511c86 OBJ0.0x829c +14000400 OBJ0.0x82a0 +fc001c02 OBJ0.0x82a4 +3bfe07ff OBJ0.0x82a8 +0c00dc43 OBJ0.0x82ac +68000000 OBJ0.0x82b0 +00c0df85 OBJ0.0x82b4 +94000000 OBJ0.0x82b8 +00c01f85 OBJ0.0x82bc +84000000 OBJ0.0x82c0 +fc40dc03 OBJ0.0x82c4 +4800ffff OBJ0.0x82c8 +08011de2 OBJ0.0x82cc +18000000 OBJ0.0x82d0 +0c40dc03 OBJ0.0x82d4 +60000000 OBJ0.0x82d8 +20111ca5 OBJ0.0x82dc +c0000003 OBJ0.0x82e0 +fc30dc03 OBJ0.0x82e4 +4800ffff OBJ0.0x82e8 +10c0df85 OBJ0.0x82ec +94000000 OBJ0.0x82f0 +fc00dde4 OBJ0.0x82f4 +28000000 OBJ0.0x82f8 +7010dc85 OBJ0.0x82fc +c8000003 OBJ0.0x8300 +fc001c02 OBJ0.0x8304 +3801ffff OBJ0.0x8308 +00c01f85 OBJ0.0x830c +94000000 OBJ0.0x8310 +20c1df85 OBJ0.0x8314 +94000000 OBJ0.0x8318 +80109c85 OBJ0.0x831c +c0000002 OBJ0.0x8320 +3010dc85 OBJ0.0x8324 +c0000001 OBJ0.0x8328 +00401c02 OBJ0.0x832c +3bfc0000 OBJ0.0x8330 +fc53dc03 OBJ0.0x8334 +190e0000 OBJ0.0x8338 +fc01dde4 OBJ0.0x833c +28000000 OBJ0.0x8340 +0001dc03 OBJ0.0x8344 +190e4000 OBJ0.0x8348 +00000007 OBJ0.0x834c +60000003 OBJ0.0x8350 +20221fa5 OBJ0.0x8354 +84000000 OBJ0.0x8358 +0401dc04 OBJ0.0x835c +0c0e0000 OBJ0.0x8360 +24019de4 OBJ0.0x8364 +28000000 OBJ0.0x8368 +f8801c03 OBJ0.0x836c +6800ffff OBJ0.0x8370 +30c19f85 OBJ0.0x8374 +94000000 OBJ0.0x8378 +f8029c03 OBJ0.0x837c +6800ffff OBJ0.0x8380 +800001e7 OBJ0.0x8384 +40000000 OBJ0.0x8388 +00421f25 OBJ0.0x838c +54143000 OBJ0.0x8390 +8011dc85 OBJ0.0x8394 +c8000001 OBJ0.0x8398 +00401ca5 OBJ0.0x839c +9c000000 OBJ0.0x83a0 +80001de7 OBJ0.0x83a4 +40000001 OBJ0.0x83a8 +00419c85 OBJ0.0x83ac +a0000000 OBJ0.0x83b0 +1cf3dc04 OBJ0.0x83b4 +0c0e0000 OBJ0.0x83b8 +8011de85 OBJ0.0x83bc +c0000001 OBJ0.0x83c0 +1041c185 OBJ0.0x83c4 +a0000000 OBJ0.0x83c8 +206fc503 OBJ0.0x83cc +48010000 OBJ0.0x83d0 +8011dc85 OBJ0.0x83d4 +c8000001 OBJ0.0x83d8 +2475c443 OBJ0.0x83dc +190e0000 OBJ0.0x83e0 +1cb1c404 OBJ0.0x83e4 +20040000 OBJ0.0x83e8 +18a00404 OBJ0.0x83ec +20040000 OBJ0.0x83f0 +1041c485 OBJ0.0x83f4 +e8000000 OBJ0.0x83f8 +00400085 OBJ0.0x83fc +e8000000 OBJ0.0x8400 +800025e7 OBJ0.0x8404 +4003fffe OBJ0.0x8408 +00001df4 OBJ0.0x840c +40000000 OBJ0.0x8410 +80101c85 OBJ0.0x8414 +c0000001 OBJ0.0x8418 +188fdd03 OBJ0.0x841c +48010000 OBJ0.0x8420 +0091dc43 OBJ0.0x8424 +1a8e0000 OBJ0.0x8428 +000001e7 OBJ0.0x842c +40000002 OBJ0.0x8430 +e0111ea5 OBJ0.0x8434 +c0000002 OBJ0.0x8438 +a0000007 OBJ0.0x843c +60000001 OBJ0.0x8440 +00401c02 OBJ0.0x8444 +3bfc0000 OBJ0.0x8448 +fc53dc03 OBJ0.0x844c +190e0000 OBJ0.0x8450 +0001dc03 OBJ0.0x8454 +190e4000 OBJ0.0x8458 +0401dc04 OBJ0.0x845c +0c0e0000 OBJ0.0x8460 +600001e7 OBJ0.0x8464 +40000000 OBJ0.0x8468 +fc001de2 OBJ0.0x846c +1bffffff OBJ0.0x8470 +00401c05 OBJ0.0x8474 +14000000 OBJ0.0x8478 +80001de7 OBJ0.0x847c +40000000 OBJ0.0x8480 +00401c85 OBJ0.0x8484 +a0000000 OBJ0.0x8488 +fc000003 OBJ0.0x848c +4800ffff OBJ0.0x8490 +00400085 OBJ0.0x8494 +e8000000 OBJ0.0x8498 +800021e7 OBJ0.0x849c +4003ffff OBJ0.0x84a0 +00001df4 OBJ0.0x84a4 +40000000 OBJ0.0x84a8 +00001df4 OBJ0.0x84ac +40000000 OBJ0.0x84b0 +70101e85 OBJ0.0x84b4 +c0000003 OBJ0.0x84b8 +04001c03 OBJ0.0x84bc +4800c000 OBJ0.0x84c0 +4001dc23 OBJ0.0x84c4 +1a8ec30d OBJ0.0x84c8 +70101c85 OBJ0.0x84cc +c8000003 OBJ0.0x84d0 +000001e7 OBJ0.0x84d4 +4003fff9 OBJ0.0x84d8 +34015de4 OBJ0.0x84dc +28000000 OBJ0.0x84e0 +30011de4 OBJ0.0x84e4 +28000000 OBJ0.0x84e8 +00010007 OBJ0.0x84ec +100001d0 OBJ0.0x84f0 +e0111ea5 OBJ0.0x84f4 +c0000002 OBJ0.0x84f8 +a0000007 OBJ0.0x84fc +60000001 OBJ0.0x8500 +00401c02 OBJ0.0x8504 +3bfc0000 OBJ0.0x8508 +fc53dc03 OBJ0.0x850c +190e0000 OBJ0.0x8510 +0001dc03 OBJ0.0x8514 +190e4000 OBJ0.0x8518 +0401dc04 OBJ0.0x851c +0c0e0000 OBJ0.0x8520 +600001e7 OBJ0.0x8524 +40000000 OBJ0.0x8528 +fc001de2 OBJ0.0x852c +1bffffff OBJ0.0x8530 +00401c05 OBJ0.0x8534 +14000000 OBJ0.0x8538 +80001de7 OBJ0.0x853c +40000000 OBJ0.0x8540 +00401c85 OBJ0.0x8544 +a0000000 OBJ0.0x8548 +fc000003 OBJ0.0x854c +4800ffff OBJ0.0x8550 +00400085 OBJ0.0x8554 +e8000000 OBJ0.0x8558 +800021e7 OBJ0.0x855c +4003ffff OBJ0.0x8560 +00001df4 OBJ0.0x8564 +40000000 OBJ0.0x8568 +60001de7 OBJ0.0x856c +40000004 OBJ0.0x8570 +e0111ea5 OBJ0.0x8574 +c0000002 OBJ0.0x8578 +a0000007 OBJ0.0x857c +60000001 OBJ0.0x8580 +00401c02 OBJ0.0x8584 +3bfc0000 OBJ0.0x8588 +fc53dc03 OBJ0.0x858c +190e0000 OBJ0.0x8590 +0001dc03 OBJ0.0x8594 +190e4000 OBJ0.0x8598 +0401dc04 OBJ0.0x859c +0c0e0000 OBJ0.0x85a0 +600001e7 OBJ0.0x85a4 +40000000 OBJ0.0x85a8 +fc001de2 OBJ0.0x85ac +1bffffff OBJ0.0x85b0 +00401c05 OBJ0.0x85b4 +14000000 OBJ0.0x85b8 +80001de7 OBJ0.0x85bc +40000000 OBJ0.0x85c0 +00401c85 OBJ0.0x85c4 +a0000000 OBJ0.0x85c8 +fc000003 OBJ0.0x85cc +4800ffff OBJ0.0x85d0 +00400085 OBJ0.0x85d4 +e8000000 OBJ0.0x85d8 +800021e7 OBJ0.0x85dc +4003ffff OBJ0.0x85e0 +00001df4 OBJ0.0x85e4 +40000000 OBJ0.0x85e8 +b010de85 OBJ0.0x85ec +c0000000 OBJ0.0x85f0 +fc001de4 OBJ0.0x85f4 +28000000 OBJ0.0x85f8 +00111c85 OBJ0.0x85fc +c0000001 OBJ0.0x8600 +10115c85 OBJ0.0x8604 +c0000002 OBJ0.0x8608 +d0411f85 OBJ0.0x860c +84000000 OBJ0.0x8610 +fc41dc03 OBJ0.0x8614 +190e0000 OBJ0.0x8618 +a00001e7 OBJ0.0x861c +40000001 OBJ0.0x8620 +3c01dc23 OBJ0.0x8624 +1a0ec30d OBJ0.0x8628 +04001c03 OBJ0.0x862c +4800c000 OBJ0.0x8630 +400001e7 OBJ0.0x8634 +40000001 OBJ0.0x8638 +80111c85 OBJ0.0x863c +c0000002 OBJ0.0x8640 +30115c85 OBJ0.0x8644 +c0000001 OBJ0.0x8648 +30411f85 OBJ0.0x864c +84000000 OBJ0.0x8650 +0c41dc03 OBJ0.0x8654 +190e0000 OBJ0.0x8658 +600001e7 OBJ0.0x865c +4003fffe OBJ0.0x8660 +80109c85 OBJ0.0x8664 +c0000002 OBJ0.0x8668 +3010dc85 OBJ0.0x866c +c0000001 OBJ0.0x8670 +30201f85 OBJ0.0x8674 +84000000 OBJ0.0x8678 +20031c03 OBJ0.0x867c +6000c000 OBJ0.0x8680 +60035c13 OBJ0.0x8684 +5800c000 OBJ0.0x8688 +fc031de4 OBJ0.0x868c +28000000 OBJ0.0x8690 +fc035df4 OBJ0.0x8694 +28000000 OBJ0.0x8698 +fccfdd03 OBJ0.0x869c +48010000 OBJ0.0x86a0 +fcd1dc43 OBJ0.0x86a4 +1a8e0000 OBJ0.0x86a8 +800001e7 OBJ0.0x86ac +40000001 OBJ0.0x86b0 +80111c85 OBJ0.0x86b4 +c0000002 OBJ0.0x86b8 +30115c85 OBJ0.0x86bc +c0000001 OBJ0.0x86c0 +d010de85 OBJ0.0x86c4 +c0000000 OBJ0.0x86c8 +30401f85 OBJ0.0x86cc +84000000 OBJ0.0x86d0 +0c01dc03 OBJ0.0x86d4 +1a8e0000 OBJ0.0x86d8 +c00001e7 OBJ0.0x86dc +40000001 OBJ0.0x86e0 +90101c85 OBJ0.0x86e4 +c0000003 OBJ0.0x86e8 +fc011de4 OBJ0.0x86ec +28000000 OBJ0.0x86f0 +fc015de4 OBJ0.0x86f4 +28000000 OBJ0.0x86f8 +60001c86 OBJ0.0x86fc +14000405 OBJ0.0x8700 +b0101c85 OBJ0.0x8704 +c8000003 OBJ0.0x8708 +00001de7 OBJ0.0x870c +a8000000 OBJ0.0x8710 +e0119c85 OBJ0.0x8714 +c0000000 OBJ0.0x8718 +34015de4 OBJ0.0x871c +28000000 OBJ0.0x8720 +30011de4 OBJ0.0x8724 +28000000 OBJ0.0x8728 +0401dde2 OBJ0.0x872c +18000000 OBJ0.0x8730 +00010007 OBJ0.0x8734 +100001fc OBJ0.0x8738 +fc4fdd03 OBJ0.0x873c +48010000 OBJ0.0x8740 +fc51dc43 OBJ0.0x8744 +190e0000 OBJ0.0x8748 +000021e7 OBJ0.0x874c +a8000000 OBJ0.0x8750 +00001df4 OBJ0.0x8754 +40000000 OBJ0.0x8758 +50101e85 OBJ0.0x875c +c0000001 OBJ0.0x8760 +04001c03 OBJ0.0x8764 +4800c000 OBJ0.0x8768 +4001dc23 OBJ0.0x876c +1a8ec30d OBJ0.0x8770 +50101c85 OBJ0.0x8774 +c8000001 OBJ0.0x8778 +400001e7 OBJ0.0x877c +4003ff5a OBJ0.0x8780 +90101c85 OBJ0.0x8784 +c0000003 OBJ0.0x8788 +fc011de4 OBJ0.0x878c +28000000 OBJ0.0x8790 +fc015de4 OBJ0.0x8794 +28000000 OBJ0.0x8798 +60001c86 OBJ0.0x879c +14000405 OBJ0.0x87a0 +b0101c85 OBJ0.0x87a4 +c8000003 OBJ0.0x87a8 +00001de7 OBJ0.0x87ac +a8000000 OBJ0.0x87b0 +fc4fdd03 OBJ0.0x87b4 +48010000 OBJ0.0x87b8 +fc51dc43 OBJ0.0x87bc +190e0000 OBJ0.0x87c0 +c00001e7 OBJ0.0x87c4 +4000000f OBJ0.0x87c8 +40429c03 OBJ0.0x87cc +4801c000 OBJ0.0x87d0 +fca01c03 OBJ0.0x87d4 +6800c003 OBJ0.0x87d8 +03f0dc04 OBJ0.0x87dc +3000c3c0 OBJ0.0x87e0 +fc0fdd03 OBJ0.0x87e4 +48010000 OBJ0.0x87e8 +fff1dc43 OBJ0.0x87ec +190e0000 OBJ0.0x87f0 +00301c04 OBJ0.0x87f4 +3400c3c0 OBJ0.0x87f8 +fc52dc43 OBJ0.0x87fc +48000000 OBJ0.0x8800 +000081e7 OBJ0.0x8804 +40000002 OBJ0.0x8808 +c0a323c5 OBJ0.0x880c +87ffffff OBJ0.0x8810 +c010e003 OBJ0.0x8814 +4800c004 OBJ0.0x8818 +10322003 OBJ0.0x881c +48014000 OBJ0.0x8820 +fff26043 OBJ0.0x8824 +48000000 OBJ0.0x8828 +00002203 OBJ0.0x882c +4801c004 OBJ0.0x8830 +1000e003 OBJ0.0x8834 +5800c000 OBJ0.0x8838 +fff02143 OBJ0.0x883c +48000000 OBJ0.0x8840 +0c00e383 OBJ0.0x8844 +40000000 OBJ0.0x8848 +10002003 OBJ0.0x884c +5800c000 OBJ0.0x8850 +4032a003 OBJ0.0x8854 +2015c000 OBJ0.0x8858 +008323c5 OBJ0.0x885c +94000000 OBJ0.0x8860 +008123c5 OBJ0.0x8864 +84000000 OBJ0.0x8868 +70322003 OBJ0.0x886c +5800c000 OBJ0.0x8870 +20002083 OBJ0.0x8874 +40000000 OBJ0.0x8878 +00b2e043 OBJ0.0x887c +48000000 OBJ0.0x8880 +c0a123c5 OBJ0.0x8884 +97ffffff OBJ0.0x8888 +0c00dde2 OBJ0.0x888c +1800016b OBJ0.0x8890 +80111c85 OBJ0.0x8894 +c0000003 OBJ0.0x8898 +b0115c85 OBJ0.0x889c +c0000003 OBJ0.0x88a0 +00a0df45 OBJ0.0x88a4 +94000000 OBJ0.0x88a8 +00a01f85 OBJ0.0x88ac +84000000 OBJ0.0x88b0 +70125e85 OBJ0.0x88b4 +c0000001 OBJ0.0x88b8 +fc411c03 OBJ0.0x88bc +6800c000 OBJ0.0x88c0 +fc00dc03 OBJ0.0x88c4 +6800fbff OBJ0.0x88c8 +00a0df85 OBJ0.0x88cc +94000000 OBJ0.0x88d0 +00a01f85 OBJ0.0x88d4 +84000000 OBJ0.0x88d8 +4440dc03 OBJ0.0x88dc +6000c000 OBJ0.0x88e0 +fc511c03 OBJ0.0x88e4 +4800ffff OBJ0.0x88e8 +08015de2 OBJ0.0x88ec +18000000 OBJ0.0x88f0 +fc001c02 OBJ0.0x88f4 +3bfe07ff OBJ0.0x88f8 +0c00dc43 OBJ0.0x88fc +68000000 OBJ0.0x8900 +00a0df85 OBJ0.0x8904 +94000000 OBJ0.0x8908 +00a01f85 OBJ0.0x890c +84000000 OBJ0.0x8910 +1050dc03 OBJ0.0x8914 +60000000 OBJ0.0x8918 +f0015de2 OBJ0.0x891c +18000294 OBJ0.0x8920 +fc311c03 OBJ0.0x8924 +4800ffff OBJ0.0x8928 +10a11f85 OBJ0.0x892c +94000000 OBJ0.0x8930 +fc00dc02 OBJ0.0x8934 +3801ffff OBJ0.0x8938 +20a01c03 OBJ0.0x893c +5800c000 OBJ0.0x8940 +00a0df85 OBJ0.0x8944 +94000000 OBJ0.0x8948 +00b1df03 OBJ0.0x894c +40000000 OBJ0.0x8950 +20a15f85 OBJ0.0x8954 +94000000 OBJ0.0x8958 +fc001de4 OBJ0.0x895c +28000000 OBJ0.0x8960 +80131c85 OBJ0.0x8964 +c0000002 OBJ0.0x8968 +30135c85 OBJ0.0x896c +c0000001 OBJ0.0x8970 +00c0dc02 OBJ0.0x8974 +3bfc0000 OBJ0.0x8978 +00c11fa5 OBJ0.0x897c +84000000 OBJ0.0x8980 +fcd3dc03 OBJ0.0x8984 +190e0000 OBJ0.0x8988 +0031dc03 OBJ0.0x898c +190e4000 OBJ0.0x8990 +fc035de4 OBJ0.0x8994 +28000000 OBJ0.0x8998 +0401dc04 OBJ0.0x899c +0c0e0000 OBJ0.0x89a0 +14031de4 OBJ0.0x89a4 +28000000 OBJ0.0x89a8 +f840dc03 OBJ0.0x89ac +6800ffff OBJ0.0x89b0 +30a31f85 OBJ0.0x89b4 +94000000 OBJ0.0x89b8 +f8319c03 OBJ0.0x89bc +6800ffff OBJ0.0x89c0 +a00001e7 OBJ0.0x89c4 +40000000 OBJ0.0x89c8 +80109c85 OBJ0.0x89cc +c0000002 OBJ0.0x89d0 +3010dc85 OBJ0.0x89d4 +c0000001 OBJ0.0x89d8 +00211f25 OBJ0.0x89dc +540c4000 OBJ0.0x89e0 +00201ca5 OBJ0.0x89e4 +9c000000 OBJ0.0x89e8 +c0001de7 OBJ0.0x89ec +40000001 OBJ0.0x89f0 +a0000007 OBJ0.0x89f4 +60000001 OBJ0.0x89f8 +80139c85 OBJ0.0x89fc +c0000002 OBJ0.0x8a00 +3013dc85 OBJ0.0x8a04 +c0000001 OBJ0.0x8a08 +1cf3dc04 OBJ0.0x8a0c +0c0e0000 OBJ0.0x8a10 +00e21c85 OBJ0.0x8a14 +a0000000 OBJ0.0x8a18 +10e24185 OBJ0.0x8a1c +a0000000 OBJ0.0x8a20 +108fc503 OBJ0.0x8a24 +48010000 OBJ0.0x8a28 +1495c443 OBJ0.0x8a2c +190e0000 OBJ0.0x8a30 +24730404 OBJ0.0x8a34 +20040000 OBJ0.0x8a38 +2060c404 OBJ0.0x8a3c +20040000 OBJ0.0x8a40 +10e30485 OBJ0.0x8a44 +e8000000 OBJ0.0x8a48 +00e0c085 OBJ0.0x8a4c +e8000000 OBJ0.0x8a50 +800025e7 OBJ0.0x8a54 +4003fffe OBJ0.0x8a58 +00001df4 OBJ0.0x8a5c +40000000 OBJ0.0x8a60 +204fdd03 OBJ0.0x8a64 +48010000 OBJ0.0x8a68 +2451dc43 OBJ0.0x8a6c +1a8e0000 OBJ0.0x8a70 +200001e7 OBJ0.0x8a74 +40000002 OBJ0.0x8a78 +00111ea5 OBJ0.0x8a7c +c0000003 OBJ0.0x8a80 +70125c85 OBJ0.0x8a84 +c8000001 OBJ0.0x8a88 +a0000007 OBJ0.0x8a8c +60000001 OBJ0.0x8a90 +00401c02 OBJ0.0x8a94 +3bfc0000 OBJ0.0x8a98 +fc53dc03 OBJ0.0x8a9c +190e0000 OBJ0.0x8aa0 +0001dc03 OBJ0.0x8aa4 +190e4000 OBJ0.0x8aa8 +0401dc04 OBJ0.0x8aac +0c0e0000 OBJ0.0x8ab0 +600001e7 OBJ0.0x8ab4 +40000000 OBJ0.0x8ab8 +fc001de2 OBJ0.0x8abc +1bffffff OBJ0.0x8ac0 +00401c05 OBJ0.0x8ac4 +14000000 OBJ0.0x8ac8 +80001de7 OBJ0.0x8acc +40000000 OBJ0.0x8ad0 +00401c85 OBJ0.0x8ad4 +a0000000 OBJ0.0x8ad8 +fc000003 OBJ0.0x8adc +4800ffff OBJ0.0x8ae0 +00400085 OBJ0.0x8ae4 +e8000000 OBJ0.0x8ae8 +800021e7 OBJ0.0x8aec +4003ffff OBJ0.0x8af0 +00001df4 OBJ0.0x8af4 +40000000 OBJ0.0x8af8 +00001df4 OBJ0.0x8afc +40000000 OBJ0.0x8b00 +04001c03 OBJ0.0x8b04 +4800c000 OBJ0.0x8b08 +4001dc23 OBJ0.0x8b0c +1a8ec30d OBJ0.0x8b10 +200001e7 OBJ0.0x8b14 +4003fff9 OBJ0.0x8b18 +2c015de4 OBJ0.0x8b1c +28000000 OBJ0.0x8b20 +70125c85 OBJ0.0x8b24 +c8000001 OBJ0.0x8b28 +28011de4 OBJ0.0x8b2c +28000000 OBJ0.0x8b30 +00010007 OBJ0.0x8b34 +100001d0 OBJ0.0x8b38 +00111ea5 OBJ0.0x8b3c +c0000003 OBJ0.0x8b40 +a0000007 OBJ0.0x8b44 +60000001 OBJ0.0x8b48 +00401c02 OBJ0.0x8b4c +3bfc0000 OBJ0.0x8b50 +fc53dc03 OBJ0.0x8b54 +190e0000 OBJ0.0x8b58 +0001dc03 OBJ0.0x8b5c +190e4000 OBJ0.0x8b60 +0401dc04 OBJ0.0x8b64 +0c0e0000 OBJ0.0x8b68 +600001e7 OBJ0.0x8b6c +40000000 OBJ0.0x8b70 +fc001de2 OBJ0.0x8b74 +1bffffff OBJ0.0x8b78 +00401c05 OBJ0.0x8b7c +14000000 OBJ0.0x8b80 +80001de7 OBJ0.0x8b84 +40000000 OBJ0.0x8b88 +00401c85 OBJ0.0x8b8c +a0000000 OBJ0.0x8b90 +fc000003 OBJ0.0x8b94 +4800ffff OBJ0.0x8b98 +00400085 OBJ0.0x8b9c +e8000000 OBJ0.0x8ba0 +800021e7 OBJ0.0x8ba4 +4003ffff OBJ0.0x8ba8 +00001df4 OBJ0.0x8bac +40000000 OBJ0.0x8bb0 +60001de7 OBJ0.0x8bb4 +40000004 OBJ0.0x8bb8 +00111ea5 OBJ0.0x8bbc +c0000003 OBJ0.0x8bc0 +a0000007 OBJ0.0x8bc4 +60000001 OBJ0.0x8bc8 +00401c02 OBJ0.0x8bcc +3bfc0000 OBJ0.0x8bd0 +fc53dc03 OBJ0.0x8bd4 +190e0000 OBJ0.0x8bd8 +0001dc03 OBJ0.0x8bdc +190e4000 OBJ0.0x8be0 +0401dc04 OBJ0.0x8be4 +0c0e0000 OBJ0.0x8be8 +600001e7 OBJ0.0x8bec +40000000 OBJ0.0x8bf0 +fc001de2 OBJ0.0x8bf4 +1bffffff OBJ0.0x8bf8 +00401c05 OBJ0.0x8bfc +14000000 OBJ0.0x8c00 +80001de7 OBJ0.0x8c04 +40000000 OBJ0.0x8c08 +00401c85 OBJ0.0x8c0c +a0000000 OBJ0.0x8c10 +fc000003 OBJ0.0x8c14 +4800ffff OBJ0.0x8c18 +00400085 OBJ0.0x8c1c +e8000000 OBJ0.0x8c20 +800021e7 OBJ0.0x8c24 +4003ffff OBJ0.0x8c28 +00001df4 OBJ0.0x8c2c +40000000 OBJ0.0x8c30 +0010de85 OBJ0.0x8c34 +c0000002 OBJ0.0x8c38 +fc001de4 OBJ0.0x8c3c +28000000 OBJ0.0x8c40 +00111c85 OBJ0.0x8c44 +c0000001 OBJ0.0x8c48 +10115c85 OBJ0.0x8c4c +c0000002 OBJ0.0x8c50 +c0411f85 OBJ0.0x8c54 +84000000 OBJ0.0x8c58 +fc41dc03 OBJ0.0x8c5c +190e0000 OBJ0.0x8c60 +a00001e7 OBJ0.0x8c64 +40000001 OBJ0.0x8c68 +3c01dc23 OBJ0.0x8c6c +1a0ec30d OBJ0.0x8c70 +04001c03 OBJ0.0x8c74 +4800c000 OBJ0.0x8c78 +400001e7 OBJ0.0x8c7c +40000001 OBJ0.0x8c80 +80111c85 OBJ0.0x8c84 +c0000002 OBJ0.0x8c88 +30115c85 OBJ0.0x8c8c +c0000001 OBJ0.0x8c90 +10411f85 OBJ0.0x8c94 +84000000 OBJ0.0x8c98 +0c41dc03 OBJ0.0x8c9c +190e0000 OBJ0.0x8ca0 +600001e7 OBJ0.0x8ca4 +4003fffe OBJ0.0x8ca8 +80109c85 OBJ0.0x8cac +c0000002 OBJ0.0x8cb0 +3010dc85 OBJ0.0x8cb4 +c0000001 OBJ0.0x8cb8 +10201f85 OBJ0.0x8cbc +84000000 OBJ0.0x8cc0 +20029c03 OBJ0.0x8cc4 +6000c000 OBJ0.0x8cc8 +6002dc13 OBJ0.0x8ccc +5800c000 OBJ0.0x8cd0 +fc029de4 OBJ0.0x8cd4 +28000000 OBJ0.0x8cd8 +fc02ddf4 OBJ0.0x8cdc +28000000 OBJ0.0x8ce0 +fcafdd03 OBJ0.0x8ce4 +48010000 OBJ0.0x8ce8 +fcb1dc43 OBJ0.0x8cec +1a8e0000 OBJ0.0x8cf0 +200001e7 OBJ0.0x8cf4 +40000001 OBJ0.0x8cf8 +80111c85 OBJ0.0x8cfc +c0000002 OBJ0.0x8d00 +30115c85 OBJ0.0x8d04 +c0000001 OBJ0.0x8d08 +2010de85 OBJ0.0x8d0c +c0000001 OBJ0.0x8d10 +10401f85 OBJ0.0x8d14 +84000000 OBJ0.0x8d18 +0c01dc03 OBJ0.0x8d1c +1a8e0000 OBJ0.0x8d20 +600001e7 OBJ0.0x8d24 +40000001 OBJ0.0x8d28 +fc011de4 OBJ0.0x8d2c +28000000 OBJ0.0x8d30 +fc015de4 OBJ0.0x8d34 +28000000 OBJ0.0x8d38 +00001de7 OBJ0.0x8d3c +a8000000 OBJ0.0x8d40 +2c015de4 OBJ0.0x8d44 +28000000 OBJ0.0x8d48 +28011de4 OBJ0.0x8d4c +28000000 OBJ0.0x8d50 +80119c85 OBJ0.0x8d54 +c0000003 OBJ0.0x8d58 +9011dc85 OBJ0.0x8d5c +c0000002 OBJ0.0x8d60 +00010007 OBJ0.0x8d64 +100001fc OBJ0.0x8d68 +fc4fdd03 OBJ0.0x8d6c +48010000 OBJ0.0x8d70 +fc51dc43 OBJ0.0x8d74 +190e0000 OBJ0.0x8d78 +000021e7 OBJ0.0x8d7c +a8000000 OBJ0.0x8d80 +00001df4 OBJ0.0x8d84 +40000000 OBJ0.0x8d88 +60101e85 OBJ0.0x8d8c +c0000001 OBJ0.0x8d90 +04001c03 OBJ0.0x8d94 +4800c000 OBJ0.0x8d98 +4001dc23 OBJ0.0x8d9c +1a8ec30d OBJ0.0x8da0 +60101c85 OBJ0.0x8da4 +c8000001 OBJ0.0x8da8 +800001e7 OBJ0.0x8dac +4003ff34 OBJ0.0x8db0 +fc011de4 OBJ0.0x8db4 +28000000 OBJ0.0x8db8 +fc015de4 OBJ0.0x8dbc +28000000 OBJ0.0x8dc0 +00001de7 OBJ0.0x8dc4 +a8000000 OBJ0.0x8dc8 +fc4fdd03 OBJ0.0x8dcc +48010000 OBJ0.0x8dd0 +fc51dc43 OBJ0.0x8dd4 +1a8e0000 OBJ0.0x8dd8 +600001e7 OBJ0.0x8ddc +40000000 OBJ0.0x8de0 +fc011de4 OBJ0.0x8de4 +28000000 OBJ0.0x8de8 +fc015de4 OBJ0.0x8dec +28000000 OBJ0.0x8df0 +00001de7 OBJ0.0x8df4 +40000001 OBJ0.0x8df8 +40411c03 OBJ0.0x8dfc +4801c000 OBJ0.0x8e00 +fc515c43 OBJ0.0x8e04 +48000000 OBJ0.0x8e08 +a0001de7 OBJ0.0x8e0c +40000000 OBJ0.0x8e10 +04209c03 OBJ0.0x8e14 +4800c000 OBJ0.0x8e18 +0021dc03 OBJ0.0x8e1c +1a8e0000 OBJ0.0x8e20 +400001e7 OBJ0.0x8e24 +4003ff2f OBJ0.0x8e28 +fc011de4 OBJ0.0x8e2c +28000000 OBJ0.0x8e30 +fc015de4 OBJ0.0x8e34 +28000000 OBJ0.0x8e38 +c0109ea5 OBJ0.0x8e3c +c0000002 OBJ0.0x8e40 +0c005de4 OBJ0.0x8e44 +28000000 OBJ0.0x8e48 +00001de7 OBJ0.0x8e4c +90000000 OBJ0.0x8e50 +200446c0 OBJ0.0x8e54 +00000000 OBJ0.0x8e58 +0800ffd0 OBJ0.0x8e5c +00000052 OBJ0.0x8e60 +00000000 OBJ0.0x8e64 +# out of band: 00000288 08106e54 +# out of band: 0000028c 0034ee00 +200145a6 OBJ0.0x8e68 +00000001 OBJ0.0x8e6c +200446c0 OBJ0.0x8e70 +00000000 OBJ0.0x8e74 +0800ffd0 OBJ0.0x8e78 +00000053 OBJ0.0x8e7c +00000000 OBJ0.0x8e80 +# out of band: 00000290 0810a340 +# out of band: 00000294 00001e00 +200348e0 OBJ0.0x8e84 +00010000 OBJ0.0x8e88 +00000001 OBJ0.0x8e8c +00008200 OBJ0.0x8e90 +200148e3 OBJ0.0x8e94 +00000000 OBJ0.0x8e98 +608648e4 OBJ0.0x8e9c +19a01c04 OBJ0.0x8ea0 +18040000 OBJ0.0x8ea4 +10001c00 OBJ0.0x8ea8 +c8000000 OBJ0.0x8eac +f8001c02 OBJ0.0x8eb0 +087fffff OBJ0.0x8eb4 +01201c04 OBJ0.0x8eb8 +10800000 OBJ0.0x8ebc +01321c04 OBJ0.0x8ec0 +14060000 OBJ0.0x8ec4 +18829c03 OBJ0.0x8ec8 +50010000 OBJ0.0x8ecc +18801c43 OBJ0.0x8ed0 +20ff0000 OBJ0.0x8ed4 +1890dc03 OBJ0.0x8ed8 +20800000 OBJ0.0x8edc +fca01e03 OBJ0.0x8ee0 +48010000 OBJ0.0x8ee4 +1c80dc03 OBJ0.0x8ee8 +20060000 OBJ0.0x8eec +fc30de43 OBJ0.0x8ef0 +48000000 OBJ0.0x8ef4 +008fdc03 OBJ0.0x8ef8 +50010000 OBJ0.0x8efc +00829c43 OBJ0.0x8f00 +20ff0000 OBJ0.0x8f04 +00929c03 OBJ0.0x8f08 +20950000 OBJ0.0x8f0c +00901c43 OBJ0.0x8f10 +20fe0000 OBJ0.0x8f14 +0c8fdc03 OBJ0.0x8f18 +20150000 OBJ0.0x8f1c +0c829c43 OBJ0.0x8f20 +20810000 OBJ0.0x8f24 +fff01c43 OBJ0.0x8f28 +48000000 OBJ0.0x8f2c +0c929c03 OBJ0.0x8f30 +20150000 OBJ0.0x8f34 +0c90dc43 OBJ0.0x8f38 +20800000 OBJ0.0x8f3c +28801c03 OBJ0.0x8f40 +48010000 OBJ0.0x8f44 +0c90dc43 OBJ0.0x8f48 +48000000 OBJ0.0x8f4c +00629c03 OBJ0.0x8f50 +50010000 OBJ0.0x8f54 +00621c43 OBJ0.0x8f58 +20ff0000 OBJ0.0x8f5c +00725c03 OBJ0.0x8f60 +20900000 OBJ0.0x8f64 +fca21e03 OBJ0.0x8f68 +48010000 OBJ0.0x8f6c +0c625c03 OBJ0.0x8f70 +20120000 OBJ0.0x8f74 +fc925e43 OBJ0.0x8f78 +48000000 OBJ0.0x8f7c +200fdc03 OBJ0.0x8f80 +50010000 OBJ0.0x8f84 +20029c43 OBJ0.0x8f88 +20ff0000 OBJ0.0x8f8c +20329c03 OBJ0.0x8f90 +20950000 OBJ0.0x8f94 +20321c43 OBJ0.0x8f98 +20fe0000 OBJ0.0x8f9c +240fdc03 OBJ0.0x8fa0 +20150000 OBJ0.0x8fa4 +24029c43 OBJ0.0x8fa8 +20910000 OBJ0.0x8fac +fff21c43 OBJ0.0x8fb0 +48000000 OBJ0.0x8fb4 +24329c03 OBJ0.0x8fb8 +20150000 OBJ0.0x8fbc +24321c43 OBJ0.0x8fc0 +20900000 OBJ0.0x8fc4 +28001c03 OBJ0.0x8fc8 +48010000 OBJ0.0x8fcc +2030dc43 OBJ0.0x8fd0 +48000000 OBJ0.0x8fd4 +100fdc03 OBJ0.0x8fd8 +50010000 OBJ0.0x8fdc +10021c43 OBJ0.0x8fe0 +20ff0000 OBJ0.0x8fe4 +10325c03 OBJ0.0x8fe8 +20910000 OBJ0.0x8fec +10321c43 OBJ0.0x8ff0 +20fe0000 OBJ0.0x8ff4 +140fdc03 OBJ0.0x8ff8 +20130000 OBJ0.0x8ffc +14021c43 OBJ0.0x9000 +20910000 OBJ0.0x9004 +fff01c43 OBJ0.0x9008 +48000000 OBJ0.0x900c +14321c03 OBJ0.0x9010 +20110000 OBJ0.0x9014 +14301c43 OBJ0.0x9018 +20800000 OBJ0.0x901c +20625c03 OBJ0.0x9020 +50010000 OBJ0.0x9024 +2060dc43 OBJ0.0x9028 +20ff0000 OBJ0.0x902c +20721c03 OBJ0.0x9030 +20860000 OBJ0.0x9034 +2440dd03 OBJ0.0x9038 +48010000 OBJ0.0x903c +00601c03 OBJ0.0x9040 +20100000 OBJ0.0x9044 +00515d43 OBJ0.0x9048 +48000000 OBJ0.0x904c +183fdd03 OBJ0.0x9050 +48010000 OBJ0.0x9054 +1c51dc43 OBJ0.0x9058 +1b0e0000 OBJ0.0x905c +fc6fdd03 OBJ0.0x9060 +48010000 OBJ0.0x9064 +fc73dc43 OBJ0.0x9068 +1a8e0000 OBJ0.0x906c +1830c103 OBJ0.0x9070 +48010000 OBJ0.0x9074 +1c514143 OBJ0.0x9078 +48000000 OBJ0.0x907c +18301d03 OBJ0.0x9080 +48010000 OBJ0.0x9084 +1c51dc43 OBJ0.0x9088 +1b0e0000 OBJ0.0x908c +0c011c04 OBJ0.0x9090 +20000000 OBJ0.0x9094 +1c514143 OBJ0.0x9098 +48000000 OBJ0.0x909c +1bf125c3 OBJ0.0x90a0 +68000000 OBJ0.0x90a4 +1ff165c3 OBJ0.0x90a8 +68000000 OBJ0.0x90ac +00001de7 OBJ0.0x90b0 +90000000 OBJ0.0x90b4 +200446c0 OBJ0.0x90b8 +00000000 OBJ0.0x90bc +0800ffd0 OBJ0.0x90c0 +00000054 OBJ0.0x90c4 +00000000 OBJ0.0x90c8 +# out of band: 00000298 0810a35c +# out of band: 0000029c 00024a00 +200145a6 OBJ0.0x90cc +00000001 OBJ0.0x90d0 +200446c0 OBJ0.0x90d4 +00000000 OBJ0.0x90d8 +0800ffd0 OBJ0.0x90dc +00000055 OBJ0.0x90e0 +00000000 OBJ0.0x90e4 +# out of band: 000002a0 0810a5a4 +# out of band: 000002a4 00001e00 +200348e0 OBJ0.0x90e8 +00010000 OBJ0.0x90ec +00000001 OBJ0.0x90f0 +00007f00 OBJ0.0x90f4 +200148e3 OBJ0.0x90f8 +00000000 OBJ0.0x90fc +609648e4 OBJ0.0x9100 +10425f85 OBJ0.0x9104 +84000000 OBJ0.0x9108 +00000007 OBJ0.0x910c +68000009 OBJ0.0x9110 +24901c04 OBJ0.0x9114 +54000000 OBJ0.0x9118 +0071dc23 OBJ0.0x911c +1a0e0000 OBJ0.0x9120 +400001e7 OBJ0.0x9124 +40000008 OBJ0.0x9128 +fc701c03 OBJ0.0x912c +4800ffff OBJ0.0x9130 +0800dde2 OBJ0.0x9134 +18000000 OBJ0.0x9138 +2401dde4 OBJ0.0x913c +28000000 OBJ0.0x9140 +0030dc03 OBJ0.0x9144 +60000000 OBJ0.0x9148 +fc321c03 OBJ0.0x914c +4800ffff OBJ0.0x9150 +2481dc03 OBJ0.0x9154 +1a0e0000 OBJ0.0x9158 +600001e7 OBJ0.0x915c +40000007 OBJ0.0x9160 +fc00dde4 OBJ0.0x9164 +28000000 OBJ0.0x9168 +24829c03 OBJ0.0x916c +68000000 OBJ0.0x9170 +c0000007 OBJ0.0x9174 +60000006 OBJ0.0x9178 +2881dc03 OBJ0.0x917c +1a8e0000 OBJ0.0x9180 +400001e7 OBJ0.0x9184 +40000006 OBJ0.0x9188 +10425c03 OBJ0.0x918c +4801c000 OBJ0.0x9190 +40000007 OBJ0.0x9194 +60000002 OBJ0.0x9198 +0092dc02 OBJ0.0x919c +3bfc0000 OBJ0.0x91a0 +17f29c43 OBJ0.0x91a4 +48000000 OBJ0.0x91a8 +0c825c03 OBJ0.0x91ac +60000000 OBJ0.0x91b0 +00b1dc03 OBJ0.0x91b4 +190e4000 OBJ0.0x91b8 +fca3dc03 OBJ0.0x91bc +190e0000 OBJ0.0x91c0 +27f25dc3 OBJ0.0x91c4 +68000000 OBJ0.0x91c8 +0401dc04 OBJ0.0x91cc +0c0e0000 OBJ0.0x91d0 +24725c03 OBJ0.0x91d4 +68000000 OBJ0.0x91d8 +600001e7 OBJ0.0x91dc +40000000 OBJ0.0x91e0 +1041dd25 OBJ0.0x91e4 +54125000 OBJ0.0x91e8 +10401ca5 OBJ0.0x91ec +9c000000 OBJ0.0x91f0 +a0001de7 OBJ0.0x91f4 +40000000 OBJ0.0x91f8 +10429c85 OBJ0.0x91fc +a0000000 OBJ0.0x9200 +1ca3c003 OBJ0.0x9204 +190e0000 OBJ0.0x9208 +2892c004 OBJ0.0x920c +20020000 OBJ0.0x9210 +1042c085 OBJ0.0x9214 +e8000000 OBJ0.0x9218 +600021e7 OBJ0.0x921c +4003ffff OBJ0.0x9220 +1ca1dc13 OBJ0.0x9224 +1a8e0000 OBJ0.0x9228 +400001e7 OBJ0.0x922c +40000003 OBJ0.0x9230 +08619e03 OBJ0.0x9234 +6000c000 OBJ0.0x9238 +f0025de2 OBJ0.0x923c +18000294 OBJ0.0x9240 +7c001c03 OBJ0.0x9244 +6800c000 OBJ0.0x9248 +00619c86 OBJ0.0x924c +14000405 OBJ0.0x9250 +2042dc03 OBJ0.0x9254 +5800c000 OBJ0.0x9258 +58029c03 OBJ0.0x925c +6000c000 OBJ0.0x9260 +18319c03 OBJ0.0x9264 +20090000 OBJ0.0x9268 +fc30dc03 OBJ0.0x926c +6800c000 OBJ0.0x9270 +17f1dc43 OBJ0.0x9274 +48000000 OBJ0.0x9278 +40611c03 OBJ0.0x927c +4801c000 OBJ0.0x9280 +40625f45 OBJ0.0x9284 +94000000 OBJ0.0x9288 +40621f85 OBJ0.0x928c +84000000 OBJ0.0x9290 +40325c03 OBJ0.0x9294 +6000c000 OBJ0.0x9298 +fc80dc02 OBJ0.0x929c +3bff03ff OBJ0.0x92a0 +24321c43 OBJ0.0x92a4 +68000000 OBJ0.0x92a8 +20525c03 OBJ0.0x92ac +5800c000 OBJ0.0x92b0 +40621f85 OBJ0.0x92b4 +94000000 OBJ0.0x92b8 +4060df85 OBJ0.0x92bc +84000000 OBJ0.0x92c0 +2c521f03 OBJ0.0x92c4 +40000000 OBJ0.0x92c8 +fc715c43 OBJ0.0x92cc +48000000 OBJ0.0x92d0 +50621f85 OBJ0.0x92d4 +94000000 OBJ0.0x92d8 +606fdfa5 OBJ0.0x92dc +94000000 OBJ0.0x92e0 +fc301c02 OBJ0.0x92e4 +3be0ffff OBJ0.0x92e8 +28001c43 OBJ0.0x92ec +68000000 OBJ0.0x92f0 +40601f85 OBJ0.0x92f4 +94000000 OBJ0.0x92f8 +00001de7 OBJ0.0x92fc +a8000000 OBJ0.0x9300 +1041df85 OBJ0.0x9304 +84000000 OBJ0.0x9308 +fc00dde4 OBJ0.0x930c +28000000 OBJ0.0x9310 +1c025df4 OBJ0.0x9314 +28000000 OBJ0.0x9318 +04925c03 OBJ0.0x931c +5800c000 OBJ0.0x9320 +0430dc13 OBJ0.0x9324 +4800c000 OBJ0.0x9328 +2481dc03 OBJ0.0x932c +198e0000 OBJ0.0x9330 +c00001e7 OBJ0.0x9334 +4003fff8 OBJ0.0x9338 +fc011de4 OBJ0.0x933c +28000000 OBJ0.0x9340 +fc015de4 OBJ0.0x9344 +28000000 OBJ0.0x9348 +00001de7 OBJ0.0x934c +a8000000 OBJ0.0x9350 +00001de7 OBJ0.0x9354 +90000000 OBJ0.0x9358 +200446c0 OBJ0.0x935c +00000000 OBJ0.0x9360 +0800ffd0 OBJ0.0x9364 +00000056 OBJ0.0x9368 +00000000 OBJ0.0x936c +# out of band: 000002a8 0810a5c0 +# out of band: 000002ac 00028a00 +200145a6 OBJ0.0x9370 +00000001 OBJ0.0x9374 +200446c0 OBJ0.0x9378 +00000000 OBJ0.0x937c +0800ffd0 OBJ0.0x9380 +00000057 OBJ0.0x9384 +00000000 OBJ0.0x9388 +# out of band: 000002b0 0810a848 +# out of band: 000002b4 00001e00 +200348e0 OBJ0.0x938c +00010000 OBJ0.0x9390 +00000001 OBJ0.0x9394 +00007c00 OBJ0.0x9398 +200148e3 OBJ0.0x939c +00000000 OBJ0.0x93a0 +608e48e4 OBJ0.0x93a4 +19a01c04 OBJ0.0x93a8 +18040000 OBJ0.0x93ac +10001c00 OBJ0.0x93b0 +c8000000 OBJ0.0x93b4 +f8001c02 OBJ0.0x93b8 +087fffff OBJ0.0x93bc +01201c04 OBJ0.0x93c0 +10800000 OBJ0.0x93c4 +01321c04 OBJ0.0x93c8 +14060000 OBJ0.0x93cc +18829c03 OBJ0.0x93d0 +50010000 OBJ0.0x93d4 +18801c43 OBJ0.0x93d8 +20ff0000 OBJ0.0x93dc +1890dc03 OBJ0.0x93e0 +20800000 OBJ0.0x93e4 +fca01e03 OBJ0.0x93e8 +48010000 OBJ0.0x93ec +1c80dc03 OBJ0.0x93f0 +20060000 OBJ0.0x93f4 +fc30de43 OBJ0.0x93f8 +48000000 OBJ0.0x93fc +008fdc03 OBJ0.0x9400 +50010000 OBJ0.0x9404 +00829c43 OBJ0.0x9408 +20ff0000 OBJ0.0x940c +00929c03 OBJ0.0x9410 +20950000 OBJ0.0x9414 +00901c43 OBJ0.0x9418 +20fe0000 OBJ0.0x941c +0c8fdc03 OBJ0.0x9420 +20150000 OBJ0.0x9424 +0c829c43 OBJ0.0x9428 +20810000 OBJ0.0x942c +fff01c43 OBJ0.0x9430 +48000000 OBJ0.0x9434 +0c929c03 OBJ0.0x9438 +20150000 OBJ0.0x943c +0c90dc43 OBJ0.0x9440 +20800000 OBJ0.0x9444 +28801c03 OBJ0.0x9448 +48010000 OBJ0.0x944c +0c90dc43 OBJ0.0x9450 +48000000 OBJ0.0x9454 +00629c03 OBJ0.0x9458 +50010000 OBJ0.0x945c +00621c43 OBJ0.0x9460 +20ff0000 OBJ0.0x9464 +00725c03 OBJ0.0x9468 +20900000 OBJ0.0x946c +fca21e03 OBJ0.0x9470 +48010000 OBJ0.0x9474 +0c625c03 OBJ0.0x9478 +20120000 OBJ0.0x947c +fc925e43 OBJ0.0x9480 +48000000 OBJ0.0x9484 +200fdc03 OBJ0.0x9488 +50010000 OBJ0.0x948c +20029c43 OBJ0.0x9490 +20ff0000 OBJ0.0x9494 +20329c03 OBJ0.0x9498 +20950000 OBJ0.0x949c +20321c43 OBJ0.0x94a0 +20fe0000 OBJ0.0x94a4 +240fdc03 OBJ0.0x94a8 +20150000 OBJ0.0x94ac +24029c43 OBJ0.0x94b0 +20910000 OBJ0.0x94b4 +fff21c43 OBJ0.0x94b8 +48000000 OBJ0.0x94bc +24329c03 OBJ0.0x94c0 +20150000 OBJ0.0x94c4 +24321c43 OBJ0.0x94c8 +20900000 OBJ0.0x94cc +28001c03 OBJ0.0x94d0 +48010000 OBJ0.0x94d4 +2030dc43 OBJ0.0x94d8 +48000000 OBJ0.0x94dc +100fdc03 OBJ0.0x94e0 +50010000 OBJ0.0x94e4 +10021c43 OBJ0.0x94e8 +20ff0000 OBJ0.0x94ec +10325c03 OBJ0.0x94f0 +20910000 OBJ0.0x94f4 +10321c43 OBJ0.0x94f8 +20fe0000 OBJ0.0x94fc +140fdc03 OBJ0.0x9500 +20130000 OBJ0.0x9504 +14001c43 OBJ0.0x9508 +20910000 OBJ0.0x950c +fff21c43 OBJ0.0x9510 +48000000 OBJ0.0x9514 +14301c03 OBJ0.0x9518 +20010000 OBJ0.0x951c +1430dc43 OBJ0.0x9520 +20900000 OBJ0.0x9524 +18025c03 OBJ0.0x9528 +50010000 OBJ0.0x952c +18021c43 OBJ0.0x9530 +20ff0000 OBJ0.0x9534 +18321c03 OBJ0.0x9538 +20900000 OBJ0.0x953c +24411d03 OBJ0.0x9540 +48010000 OBJ0.0x9544 +1c021c03 OBJ0.0x9548 +20100000 OBJ0.0x954c +20515d43 OBJ0.0x9550 +48000000 OBJ0.0x9554 +184fdd03 OBJ0.0x9558 +48010000 OBJ0.0x955c +1c51dc43 OBJ0.0x9560 +1b0e0000 OBJ0.0x9564 +18410103 OBJ0.0x9568 +48010000 OBJ0.0x956c +1c514143 OBJ0.0x9570 +48000000 OBJ0.0x9574 +04000003 OBJ0.0x9578 +4801c000 OBJ0.0x957c +fc30c043 OBJ0.0x9580 +48000000 OBJ0.0x9584 +184fdd03 OBJ0.0x9588 +48010000 OBJ0.0x958c +1c51dc43 OBJ0.0x9590 +1b0e0000 OBJ0.0x9594 +04011c03 OBJ0.0x9598 +4801c000 OBJ0.0x959c +fc315c43 OBJ0.0x95a0 +48000000 OBJ0.0x95a4 +fc6fdd03 OBJ0.0x95a8 +48010000 OBJ0.0x95ac +00411c04 OBJ0.0x95b0 +20000000 OBJ0.0x95b4 +0c515c04 OBJ0.0x95b8 +20000000 OBJ0.0x95bc +fc73dc43 OBJ0.0x95c0 +1a8e0000 OBJ0.0x95c4 +1bf125c3 OBJ0.0x95c8 +68000000 OBJ0.0x95cc +1ff165c3 OBJ0.0x95d0 +68000000 OBJ0.0x95d4 +00001de7 OBJ0.0x95d8 +90000000 OBJ0.0x95dc +200446c0 OBJ0.0x95e0 +00000000 OBJ0.0x95e4 +0800ffd0 OBJ0.0x95e8 +00000058 OBJ0.0x95ec +00000000 OBJ0.0x95f0 +# out of band: 000002b8 0810a864 +# out of band: 000002bc 00026a00 +200145a6 OBJ0.0x95f4 +00000001 OBJ0.0x95f8 +200446c0 OBJ0.0x95fc +00000000 OBJ0.0x9600 +0800ffd0 OBJ0.0x9604 +00000059 OBJ0.0x9608 +00000000 OBJ0.0x960c +# out of band: 000002c0 0810aacc +# out of band: 000002c4 00001e00 +200348e0 OBJ0.0x9610 +00010000 OBJ0.0x9614 +00000001 OBJ0.0x9618 +00007500 OBJ0.0x961c +200148e3 OBJ0.0x9620 +00000000 OBJ0.0x9624 +618448e4 OBJ0.0x9628 +00701c24 OBJ0.0x962c +49c00000 OBJ0.0x9630 +0000dc04 OBJ0.0x9634 +2c000000 OBJ0.0x9638 +80105d03 OBJ0.0x963c +4800c000 OBJ0.0x9640 +00001c03 OBJ0.0x9644 +78000000 OBJ0.0x9648 +00109c85 OBJ0.0x964c +c8000000 OBJ0.0x9650 +0c01dc03 OBJ0.0x9654 +1a8e0000 OBJ0.0x9658 +000001e7 OBJ0.0x965c +40000017 OBJ0.0x9660 +e0001de4 OBJ0.0x9664 +28004405 OBJ0.0x9668 +c0000007 OBJ0.0x966c +60000002 OBJ0.0x9670 +20001c03 OBJ0.0x9674 +4801c001 OBJ0.0x9678 +00001c02 OBJ0.0x967c +3bfc0000 OBJ0.0x9680 +f3f09c43 OBJ0.0x9684 +48004405 OBJ0.0x9688 +0001dc03 OBJ0.0x968c +190e4000 OBJ0.0x9690 +fc23dc03 OBJ0.0x9694 +190e0000 OBJ0.0x9698 +10109c85 OBJ0.0x969c +c8000000 OBJ0.0x96a0 +0401dc04 OBJ0.0x96a4 +0c0e0000 OBJ0.0x96a8 +c00001e7 OBJ0.0x96ac +40000000 OBJ0.0x96b0 +e0009de4 OBJ0.0x96b4 +28004405 OBJ0.0x96b8 +1010dc85 OBJ0.0x96bc +c0000000 OBJ0.0x96c0 +fc001de2 OBJ0.0x96c4 +1bffffff OBJ0.0x96c8 +20209c03 OBJ0.0x96cc +4800c001 OBJ0.0x96d0 +00201c05 OBJ0.0x96d4 +14000000 OBJ0.0x96d8 +e0001de7 OBJ0.0x96dc +40000000 OBJ0.0x96e0 +e0009de4 OBJ0.0x96e4 +28004405 OBJ0.0x96e8 +1010dc85 OBJ0.0x96ec +c0000000 OBJ0.0x96f0 +20209c03 OBJ0.0x96f4 +4800c001 OBJ0.0x96f8 +00201c85 OBJ0.0x96fc +a0000000 OBJ0.0x9700 +fc000003 OBJ0.0x9704 +4800ffff OBJ0.0x9708 +00200085 OBJ0.0x970c +e8000000 OBJ0.0x9710 +200021e7 OBJ0.0x9714 +4003ffff OBJ0.0x9718 +e0009df4 OBJ0.0x971c +28004405 OBJ0.0x9720 +1010dc85 OBJ0.0x9724 +c0000000 OBJ0.0x9728 +20209c03 OBJ0.0x972c +4800c001 OBJ0.0x9730 +00201f85 OBJ0.0x9734 +84000000 OBJ0.0x9738 +fc01dc03 OBJ0.0x973c +1a8e0000 OBJ0.0x9740 +600001e7 OBJ0.0x9744 +40000013 OBJ0.0x9748 +e0001de4 OBJ0.0x974c +28004405 OBJ0.0x9750 +10109c85 OBJ0.0x9754 +c0000000 OBJ0.0x9758 +e0000007 OBJ0.0x975c +60000002 OBJ0.0x9760 +20001c03 OBJ0.0x9764 +4800c001 OBJ0.0x9768 +00001c02 OBJ0.0x976c +3bfc0000 OBJ0.0x9770 +fc23dc03 OBJ0.0x9774 +190e0000 OBJ0.0x9778 +0001dc03 OBJ0.0x977c +190e4000 OBJ0.0x9780 +0401dc04 OBJ0.0x9784 +0c0e0000 OBJ0.0x9788 +e00001e7 OBJ0.0x978c +40000000 OBJ0.0x9790 +e0009de4 OBJ0.0x9794 +28004405 OBJ0.0x9798 +1010dc85 OBJ0.0x979c +c0000000 OBJ0.0x97a0 +00001de2 OBJ0.0x97a4 +1a000000 OBJ0.0x97a8 +20209c03 OBJ0.0x97ac +4800c001 OBJ0.0x97b0 +002fdd25 OBJ0.0x97b4 +54000000 OBJ0.0x97b8 +00201ca5 OBJ0.0x97bc +9c000000 OBJ0.0x97c0 +20001de7 OBJ0.0x97c4 +40000001 OBJ0.0x97c8 +e0011de4 OBJ0.0x97cc +28004405 OBJ0.0x97d0 +10115c85 OBJ0.0x97d4 +c0000000 OBJ0.0x97d8 +20411c03 OBJ0.0x97dc +4800c001 OBJ0.0x97e0 +00401c85 OBJ0.0x97e4 +a0000000 OBJ0.0x97e8 +fc03c003 OBJ0.0x97ec +190e0000 OBJ0.0x97f0 +0000c1e2 OBJ0.0x97f4 +1a000000 OBJ0.0x97f8 +0030c004 OBJ0.0x97fc +20020000 OBJ0.0x9800 +0040c085 OBJ0.0x9804 +e8000000 OBJ0.0x9808 +e00021e7 OBJ0.0x980c +4003fffe OBJ0.0x9810 +fc01dc13 OBJ0.0x9814 +1a8e0000 OBJ0.0x9818 +000001e7 OBJ0.0x981c +40000010 OBJ0.0x9820 +c3f1dc03 OBJ0.0x9824 +190e4405 OBJ0.0x9828 +200001e7 OBJ0.0x982c +4000000d OBJ0.0x9830 +fc001de4 OBJ0.0x9834 +28000000 OBJ0.0x9838 +20101c85 OBJ0.0x983c +c8000000 OBJ0.0x9840 +e0001de4 OBJ0.0x9844 +28004405 OBJ0.0x9848 +40101c85 OBJ0.0x984c +c8000000 OBJ0.0x9850 +f0001de4 OBJ0.0x9854 +28004405 OBJ0.0x9858 +50101c85 OBJ0.0x985c +c8000000 OBJ0.0x9860 +fc001de4 OBJ0.0x9864 +28000000 OBJ0.0x9868 +30101c85 OBJ0.0x986c +c8000000 OBJ0.0x9870 +40109ca5 OBJ0.0x9874 +c0000000 OBJ0.0x9878 +10201f85 OBJ0.0x987c +84000000 OBJ0.0x9880 +20009c03 OBJ0.0x9884 +6000c000 OBJ0.0x9888 +60001c03 OBJ0.0x988c +5800c000 OBJ0.0x9890 +fc2fdd03 OBJ0.0x9894 +48010000 OBJ0.0x9898 +60109c85 OBJ0.0x989c +c8000000 OBJ0.0x98a0 +70101c85 OBJ0.0x98a4 +c8000000 OBJ0.0x98a8 +fc01dc43 OBJ0.0x98ac +1a8e0000 OBJ0.0x98b0 +1c009c04 OBJ0.0x98b4 +080e0000 OBJ0.0x98b8 +c00021e7 OBJ0.0x98bc +40000004 OBJ0.0x98c0 +60111ca5 OBJ0.0x98c4 +c0000000 OBJ0.0x98c8 +00401f85 OBJ0.0x98cc +84000000 OBJ0.0x98d0 +3c001c03 OBJ0.0x98d4 +6000c000 OBJ0.0x98d8 +7c001c03 OBJ0.0x98dc +5800c000 OBJ0.0x98e0 +0401dc23 OBJ0.0x98e4 +190ec000 OBJ0.0x98e8 +600001e7 OBJ0.0x98ec +40000001 OBJ0.0x98f0 +60111ca5 OBJ0.0x98f4 +c0000000 OBJ0.0x98f8 +2010dc85 OBJ0.0x98fc +c0000000 OBJ0.0x9900 +10401f85 OBJ0.0x9904 +84000000 OBJ0.0x9908 +0830dc03 OBJ0.0x990c +6000c000 OBJ0.0x9910 +6030dc86 OBJ0.0x9914 +14000405 OBJ0.0x9918 +08011de2 OBJ0.0x991c +18000000 OBJ0.0x9920 +fc30dc03 OBJ0.0x9924 +4800ffff OBJ0.0x9928 +0c40dc03 OBJ0.0x992c +60000000 OBJ0.0x9930 +fc30dc03 OBJ0.0x9934 +4800ffff OBJ0.0x9938 +0c01dc03 OBJ0.0x993c +190e0000 OBJ0.0x9940 +400001e7 OBJ0.0x9944 +40000000 OBJ0.0x9948 +1c71dc04 OBJ0.0x994c +0c0e0000 OBJ0.0x9950 +20001de7 OBJ0.0x9954 +40000000 OBJ0.0x9958 +1cf1dc04 OBJ0.0x995c +0c0e0000 OBJ0.0x9960 +200001e7 OBJ0.0x9964 +40000002 OBJ0.0x9968 +60109ea5 OBJ0.0x996c +c0000000 OBJ0.0x9970 +40119ca5 OBJ0.0x9974 +c0000000 OBJ0.0x9978 +30201f85 OBJ0.0x997c +84000000 OBJ0.0x9980 +0c015de4 OBJ0.0x9984 +28000000 OBJ0.0x9988 +08011de4 OBJ0.0x998c +28000000 OBJ0.0x9990 +10601f85 OBJ0.0x9994 +94000000 OBJ0.0x9998 +00010007 OBJ0.0x999c +100001d0 OBJ0.0x99a0 +40109ca5 OBJ0.0x99a4 +c0000000 OBJ0.0x99a8 +10201f85 OBJ0.0x99ac +84000000 OBJ0.0x99b0 +20009c03 OBJ0.0x99b4 +6000c000 OBJ0.0x99b8 +60001c03 OBJ0.0x99bc +5800c000 OBJ0.0x99c0 +fc2fdd03 OBJ0.0x99c4 +48010000 OBJ0.0x99c8 +60109c85 OBJ0.0x99cc +c8000000 OBJ0.0x99d0 +70101c85 OBJ0.0x99d4 +c8000000 OBJ0.0x99d8 +fc01dc43 OBJ0.0x99dc +1a8e0000 OBJ0.0x99e0 +1c009c04 OBJ0.0x99e4 +080e0000 OBJ0.0x99e8 +400001e7 OBJ0.0x99ec +4003fffb OBJ0.0x99f0 +fc21dc03 OBJ0.0x99f4 +1a8e0000 OBJ0.0x99f8 +400021e7 OBJ0.0x99fc +40000004 OBJ0.0x9a00 +60111ca5 OBJ0.0x9a04 +c0000000 OBJ0.0x9a08 +30401f85 OBJ0.0x9a0c +84000000 OBJ0.0x9a10 +20011c03 OBJ0.0x9a14 +6000c000 OBJ0.0x9a18 +60015c03 OBJ0.0x9a1c +5800c000 OBJ0.0x9a20 +fc4fdd03 OBJ0.0x9a24 +48010000 OBJ0.0x9a28 +fc51dc43 OBJ0.0x9a2c +1a8e0000 OBJ0.0x9a30 +800021e7 OBJ0.0x9a34 +40000002 OBJ0.0x9a38 +00401f85 OBJ0.0x9a3c +84000000 OBJ0.0x9a40 +3c001c03 OBJ0.0x9a44 +6000c000 OBJ0.0x9a48 +7c001c03 OBJ0.0x9a4c +5800c000 OBJ0.0x9a50 +fc03dc23 OBJ0.0x9a54 +1a8e0000 OBJ0.0x9a58 +e00005e7 OBJ0.0x9a5c +40000001 OBJ0.0x9a60 +10401f85 OBJ0.0x9a64 +84000000 OBJ0.0x9a68 +2010dc85 OBJ0.0x9a6c +c0000000 OBJ0.0x9a70 +08019de2 OBJ0.0x9a74 +18000000 OBJ0.0x9a78 +0830dc03 OBJ0.0x9a7c +6000c000 OBJ0.0x9a80 +6030dc86 OBJ0.0x9a84 +14000405 OBJ0.0x9a88 +fc30dc03 OBJ0.0x9a8c +4800ffff OBJ0.0x9a90 +0c60dc03 OBJ0.0x9a94 +60000000 OBJ0.0x9a98 +fc30dc03 OBJ0.0x9a9c +4800ffff OBJ0.0x9aa0 +0c03dc03 OBJ0.0x9aa4 +1a8e0000 OBJ0.0x9aa8 +a00005e7 OBJ0.0x9aac +40000000 OBJ0.0x9ab0 +30401f85 OBJ0.0x9ab4 +84000000 OBJ0.0x9ab8 +60119ca5 OBJ0.0x9abc +c0000000 OBJ0.0x9ac0 +30601f85 OBJ0.0x9ac4 +94000000 OBJ0.0x9ac8 +00010007 OBJ0.0x9acc +100001d0 OBJ0.0x9ad0 +a0001de7 OBJ0.0x9ad4 +40000000 OBJ0.0x9ad8 +10001de4 OBJ0.0x9adc +28000000 OBJ0.0x9ae0 +1c009c04 OBJ0.0x9ae4 +080e0000 OBJ0.0x9ae8 +60101c85 OBJ0.0x9aec +c8000000 OBJ0.0x9af0 +14001de4 OBJ0.0x9af4 +28000000 OBJ0.0x9af8 +70101c85 OBJ0.0x9afc +c8000000 OBJ0.0x9b00 +fc21dc03 OBJ0.0x9b04 +1a8e0000 OBJ0.0x9b08 +c00001e7 OBJ0.0x9b0c +4003fffb OBJ0.0x9b10 +40109ea5 OBJ0.0x9b14 +c0000000 OBJ0.0x9b18 +30101e85 OBJ0.0x9b1c +c0000000 OBJ0.0x9b20 +20209c03 OBJ0.0x9b24 +4801c000 OBJ0.0x9b28 +04001c03 OBJ0.0x9b2c +4800c000 OBJ0.0x9b30 +40109c85 OBJ0.0x9b34 +c8000000 OBJ0.0x9b38 +c001dc03 OBJ0.0x9b3c +1a8e4405 OBJ0.0x9b40 +fc30dc43 OBJ0.0x9b44 +48000000 OBJ0.0x9b48 +30101c85 OBJ0.0x9b4c +c8000000 OBJ0.0x9b50 +20109e85 OBJ0.0x9b54 +c0000000 OBJ0.0x9b58 +5010dc85 OBJ0.0x9b5c +c8000000 OBJ0.0x9b60 +04209c03 OBJ0.0x9b64 +4800c000 OBJ0.0x9b68 +20109c85 OBJ0.0x9b6c +c8000000 OBJ0.0x9b70 +e00001e7 OBJ0.0x9b74 +4003fff3 OBJ0.0x9b78 +e0001de4 OBJ0.0x9b7c +28004405 OBJ0.0x9b80 +10109c85 OBJ0.0x9b84 +c0000000 OBJ0.0x9b88 +20001c03 OBJ0.0x9b8c +4800c001 OBJ0.0x9b90 +00001c02 OBJ0.0x9b94 +3bfc0000 OBJ0.0x9b98 +fc23dc03 OBJ0.0x9b9c +190e0000 OBJ0.0x9ba0 +0001dc03 OBJ0.0x9ba4 +190e4000 OBJ0.0x9ba8 +0401dc04 OBJ0.0x9bac +0c0e0000 OBJ0.0x9bb0 +c00001e7 OBJ0.0x9bb4 +40000000 OBJ0.0x9bb8 +e0009de4 OBJ0.0x9bbc +28004405 OBJ0.0x9bc0 +1010de85 OBJ0.0x9bc4 +c0000000 OBJ0.0x9bc8 +fc001de2 OBJ0.0x9bcc +19ffffff OBJ0.0x9bd0 +20209c03 OBJ0.0x9bd4 +4800c001 OBJ0.0x9bd8 +00201ca5 OBJ0.0x9bdc +14000000 OBJ0.0x9be0 +e0001de7 OBJ0.0x9be4 +40000000 OBJ0.0x9be8 +e0009de4 OBJ0.0x9bec +28004405 OBJ0.0x9bf0 +1010dc85 OBJ0.0x9bf4 +c0000000 OBJ0.0x9bf8 +20209c03 OBJ0.0x9bfc +4800c001 OBJ0.0x9c00 +00201c85 OBJ0.0x9c04 +a0000000 OBJ0.0x9c08 +fc000002 OBJ0.0x9c0c +39ffffff OBJ0.0x9c10 +00200085 OBJ0.0x9c14 +e8000000 OBJ0.0x9c18 +200021e7 OBJ0.0x9c1c +4003ffff OBJ0.0x9c20 +00109e85 OBJ0.0x9c24 +c0000000 OBJ0.0x9c28 +80105c03 OBJ0.0x9c2c +4800c000 OBJ0.0x9c30 +00001de7 OBJ0.0x9c34 +90000000 OBJ0.0x9c38 +200446c0 OBJ0.0x9c3c +00000000 OBJ0.0x9c40 +0800ffd0 OBJ0.0x9c44 +0000005a OBJ0.0x9c48 +00000000 OBJ0.0x9c4c +# out of band: 000002c8 0810aae8 +# out of band: 000002cc 00064200 +200145a6 OBJ0.0x9c50 +00000001 OBJ0.0x9c54 +200446c0 OBJ0.0x9c58 +00000000 OBJ0.0x9c5c +0800ffd0 OBJ0.0x9c60 +0000005b OBJ0.0x9c64 +00000000 OBJ0.0x9c68 +# out of band: 000002d0 0810b128 +# out of band: 000002d4 00001e00 +200348e0 OBJ0.0x9c6c +00010000 OBJ0.0x9c70 +00000001 OBJ0.0x9c74 +00007400 OBJ0.0x9c78 +200148e3 OBJ0.0x9c7c +00000000 OBJ0.0x9c80 +601448e4 OBJ0.0x9c84 +fc4fdd03 OBJ0.0x9c88 +48010000 OBJ0.0x9c8c +fc51dc43 OBJ0.0x9c90 +1a8e0000 OBJ0.0x9c94 +c00021e7 OBJ0.0x9c98 +40000000 OBJ0.0x9c9c +c0401f45 OBJ0.0x9ca0 +87ffffff OBJ0.0x9ca4 +f001dc23 OBJ0.0x9ca8 +190ec294 OBJ0.0x9cac +600021e7 OBJ0.0x9cb0 +40000000 OBJ0.0x9cb4 +c0411c03 OBJ0.0x9cb8 +4801ffff OBJ0.0x9cbc +fc515c43 OBJ0.0x9cc0 +4800ffff OBJ0.0x9cc4 +00010007 OBJ0.0x9cc8 +100002ec OBJ0.0x9ccc +00001de7 OBJ0.0x9cd0 +90000000 OBJ0.0x9cd4 +200446c0 OBJ0.0x9cd8 +00000000 OBJ0.0x9cdc +0800ffd0 OBJ0.0x9ce0 +0000005c OBJ0.0x9ce4 +00000000 OBJ0.0x9ce8 +# out of band: 000002d8 0810b144 +# out of band: 000002dc 00008200 +200145a6 OBJ0.0x9cec +00000001 OBJ0.0x9cf0 +200446c0 OBJ0.0x9cf4 +00000000 OBJ0.0x9cf8 +0800ffd0 OBJ0.0x9cfc +0000005d OBJ0.0x9d00 +00000000 OBJ0.0x9d04 +# out of band: 000002e0 0810b1c4 +# out of band: 000002e4 00001e00 +200348e0 OBJ0.0x9d08 +00010000 OBJ0.0x9d0c +00000001 OBJ0.0x9d10 +00007200 OBJ0.0x9d14 +200148e3 OBJ0.0x9d18 +00000000 OBJ0.0x9d1c +604648e4 OBJ0.0x9d20 +00701c24 OBJ0.0x9d24 +49c00000 OBJ0.0x9d28 +0000dc04 OBJ0.0x9d2c +2c000000 OBJ0.0x9d30 +00001c03 OBJ0.0x9d34 +78000000 OBJ0.0x9d38 +0c01dc03 OBJ0.0x9d3c +1a8e0000 OBJ0.0x9d40 +a00001e7 OBJ0.0x9d44 +40000003 OBJ0.0x9d48 +e0001de4 OBJ0.0x9d4c +28004405 OBJ0.0x9d50 +e0000007 OBJ0.0x9d54 +60000001 OBJ0.0x9d58 +20011c03 OBJ0.0x9d5c +4801c001 OBJ0.0x9d60 +00401c02 OBJ0.0x9d64 +3bfc0000 OBJ0.0x9d68 +f3f15c43 OBJ0.0x9d6c +48004405 OBJ0.0x9d70 +0001dc03 OBJ0.0x9d74 +190e4000 OBJ0.0x9d78 +fc53dc03 OBJ0.0x9d7c +190e0000 OBJ0.0x9d80 +0401dc04 OBJ0.0x9d84 +0c0e0000 OBJ0.0x9d88 +600001e7 OBJ0.0x9d8c +40000000 OBJ0.0x9d90 +04001de2 OBJ0.0x9d94 +18000000 OBJ0.0x9d98 +00401c05 OBJ0.0x9d9c +14000000 OBJ0.0x9da0 +80001de7 OBJ0.0x9da4 +40000000 OBJ0.0x9da8 +00401c85 OBJ0.0x9dac +a0000000 OBJ0.0x9db0 +04000003 OBJ0.0x9db4 +4800c000 OBJ0.0x9db8 +00400085 OBJ0.0x9dbc +e8000000 OBJ0.0x9dc0 +800021e7 OBJ0.0x9dc4 +4003ffff OBJ0.0x9dc8 +00001df4 OBJ0.0x9dcc +40000000 OBJ0.0x9dd0 +00401f85 OBJ0.0x9dd4 +84000000 OBJ0.0x9dd8 +fc01dc23 OBJ0.0x9ddc +1b0e0000 OBJ0.0x9de0 +200001e7 OBJ0.0x9de4 +40000001 OBJ0.0x9de8 +e0001de4 OBJ0.0x9dec +28004405 OBJ0.0x9df0 +30011c03 OBJ0.0x9df4 +4801c001 OBJ0.0x9df8 +f3f15c43 OBJ0.0x9dfc +48004405 OBJ0.0x9e00 +004fdf85 OBJ0.0x9e04 +94000000 OBJ0.0x9e08 +00001c05 OBJ0.0x9e0c +e0000000 OBJ0.0x9e10 +00001c45 OBJ0.0x9e14 +e0000000 OBJ0.0x9e18 +f0401f85 OBJ0.0x9e1c +87ffffff OBJ0.0x9e20 +fc01dc23 OBJ0.0x9e24 +188e0000 OBJ0.0x9e28 +e00001e7 OBJ0.0x9e2c +4003fffe OBJ0.0x9e30 +00001de7 OBJ0.0x9e34 +90000000 OBJ0.0x9e38 +200446c0 OBJ0.0x9e3c +00000000 OBJ0.0x9e40 +0800ffd0 OBJ0.0x9e44 +0000005e OBJ0.0x9e48 +00000000 OBJ0.0x9e4c +# out of band: 000002e8 0810b1e0 +# out of band: 000002ec 00014a00 +200145a6 OBJ0.0x9e50 +00000001 OBJ0.0x9e54 +200446c0 OBJ0.0x9e58 +00000000 OBJ0.0x9e5c +0800ffd0 OBJ0.0x9e60 +0000005f OBJ0.0x9e64 +00000000 OBJ0.0x9e68 +# out of band: 000002f0 0810b328 +# out of band: 000002f4 00001e00 +200348e0 OBJ0.0x9e6c +00010000 OBJ0.0x9e70 +00000001 OBJ0.0x9e74 +00005500 OBJ0.0x9e78 +200148e3 OBJ0.0x9e7c +00000000 OBJ0.0x9e80 +673c48e4 OBJ0.0x9e84 +80105d03 OBJ0.0x9e88 +4800c002 OBJ0.0x9e8c +fc6fdd03 OBJ0.0x9e90 +48010000 OBJ0.0x9e94 +10029de4 OBJ0.0x9e98 +28000000 OBJ0.0x9e9c +40109c85 OBJ0.0x9ea0 +c8000000 OBJ0.0x9ea4 +20001de4 OBJ0.0x9ea8 +28000000 OBJ0.0x9eac +24011de4 OBJ0.0x9eb0 +28000000 OBJ0.0x9eb4 +fc71dc43 OBJ0.0x9eb8 +1a8e0000 OBJ0.0x9ebc +1c00dde4 OBJ0.0x9ec0 +28000000 OBJ0.0x9ec4 +1402dde4 OBJ0.0x9ec8 +28000000 OBJ0.0x9ecc +a0101c85 OBJ0.0x9ed0 +c8000001 OBJ0.0x9ed4 +b0111c85 OBJ0.0x9ed8 +c8000001 OBJ0.0x9edc +18009de4 OBJ0.0x9ee0 +28000000 OBJ0.0x9ee4 +9010dc85 OBJ0.0x9ee8 +c8000000 OBJ0.0x9eec +400001e7 OBJ0.0x9ef0 +40000000 OBJ0.0x9ef4 +fc011de2 OBJ0.0x9ef8 +1bffffff OBJ0.0x9efc +60001de7 OBJ0.0x9f00 +40000071 OBJ0.0x9f04 +00201f25 OBJ0.0x9f08 +84000000 OBJ0.0x9f0c +fc01dc23 OBJ0.0x9f10 +1a8e0000 OBJ0.0x9f14 +400001e7 OBJ0.0x9f18 +40000000 OBJ0.0x9f1c +fc011de4 OBJ0.0x9f20 +28000000 OBJ0.0x9f24 +c0001de7 OBJ0.0x9f28 +40000070 OBJ0.0x9f2c +80031de2 OBJ0.0x9f30 +1bbf2bd0 OBJ0.0x9f34 +8c00dc04 OBJ0.0x9f38 +2c000000 OBJ0.0x9f3c +fc01dc23 OBJ0.0x9f40 +1a8e0000 OBJ0.0x9f44 +c0131c85 OBJ0.0x9f48 +c8000001 OBJ0.0x9f4c +c0111ca5 OBJ0.0x9f50 +c0000001 OBJ0.0x9f54 +60129ca5 OBJ0.0x9f58 +c8000002 OBJ0.0x9f5c +e0000007 OBJ0.0x9f60 +68000027 OBJ0.0x9f64 +84031c04 OBJ0.0x9f68 +2c000000 OBJ0.0x9f6c +20329c03 OBJ0.0x9f70 +50004000 OBJ0.0x9f74 +00515c02 OBJ0.0x9f78 +3a000000 OBJ0.0x9f7c +8800dc04 OBJ0.0x9f80 +2c000000 OBJ0.0x9f84 +d8515c43 OBJ0.0x9f88 +6800c004 OBJ0.0x9f8c +2030dc03 OBJ0.0x9f90 +50004000 OBJ0.0x9f94 +c0111ca5 OBJ0.0x9f98 +c8000001 OBJ0.0x9f9c +fc52dc02 OBJ0.0x9fa0 +39ffffff OBJ0.0x9fa4 +30a0dc03 OBJ0.0x9fa8 +20064000 OBJ0.0x9fac +98029c04 OBJ0.0x9fb0 +2c000000 OBJ0.0x9fb4 +00b15c42 OBJ0.0x9fb8 +3a000000 OBJ0.0x9fbc +9c02dc04 OBJ0.0x9fc0 +2c000000 OBJ0.0x9fc4 +50a29c03 OBJ0.0x9fc8 +50004000 OBJ0.0x9fcc +c0111ca5 OBJ0.0x9fd0 +c8000001 OBJ0.0x9fd4 +50b2dc03 OBJ0.0x9fd8 +50004000 OBJ0.0x9fdc +e0111ca5 OBJ0.0x9fe0 +c8000001 OBJ0.0x9fe4 +0cc31c03 OBJ0.0x9fe8 +48000000 OBJ0.0x9fec +60b35c03 OBJ0.0x9ff0 +20144000 OBJ0.0x9ff4 +10029de4 OBJ0.0x9ff8 +28000000 OBJ0.0x9ffc +fc52dc02 OBJ0.0xa000 +39ffffff OBJ0.0xa004 +94011c04 OBJ0.0xa008 +2c000000 OBJ0.0xa00c +1c015de4 OBJ0.0xa010 +28000000 OBJ0.0xa014 +e0129ca5 OBJ0.0xa018 +c8000001 OBJ0.0xa01c +34435c03 OBJ0.0xa020 +48000000 OBJ0.0xa024 +001fdca5 OBJ0.0xa028 +c8000002 OBJ0.0xa02c +401fdca5 OBJ0.0xa030 +c8000002 OBJ0.0xa034 +20131ca5 OBJ0.0xa038 +c8000002 OBJ0.0xa03c +fc029de4 OBJ0.0xa040 +28000000 OBJ0.0xa044 +fc01dde4 OBJ0.0xa048 +28000000 OBJ0.0xa04c +fc02dde4 OBJ0.0xa050 +28000000 OBJ0.0xa054 +fc031de4 OBJ0.0xa058 +28000000 OBJ0.0xa05c +fc035de4 OBJ0.0xa060 +28000000 OBJ0.0xa064 +fc00dde4 OBJ0.0xa068 +28000000 OBJ0.0xa06c +18011de4 OBJ0.0xa070 +28000000 OBJ0.0xa074 +5011dc85 OBJ0.0xa078 +c8000000 OBJ0.0xa07c +00129ca5 OBJ0.0xa080 +c8000001 OBJ0.0xa084 +60131ca5 OBJ0.0xa088 +c8000001 OBJ0.0xa08c +4011dc85 OBJ0.0xa090 +c8000001 OBJ0.0xa094 +5012dc85 OBJ0.0xa098 +c8000001 OBJ0.0xa09c +9403dc23 OBJ0.0xa0a0 +190ec000 OBJ0.0xa0a4 +e0000007 OBJ0.0xa0a8 +60000001 OBJ0.0xa0ac +000005f4 OBJ0.0xa0b0 +40000000 OBJ0.0xa0b4 +18009de4 OBJ0.0xa0b8 +28000000 OBJ0.0xa0bc +000021e7 OBJ0.0xa0c0 +a8000000 OBJ0.0xa0c4 +40000007 OBJ0.0xa0c8 +68000001 OBJ0.0xa0cc +04411c03 OBJ0.0xa0d0 +4801c000 OBJ0.0xa0d4 +fc515c43 OBJ0.0xa0d8 +48000000 OBJ0.0xa0dc +00401f25 OBJ0.0xa0e0 +84000000 OBJ0.0xa0e4 +9401dc23 OBJ0.0xa0e8 +190ec000 OBJ0.0xa0ec +600001e7 OBJ0.0xa0f0 +40000000 OBJ0.0xa0f4 +fc01dc23 OBJ0.0xa0f8 +1a8e0000 OBJ0.0xa0fc +000021e7 OBJ0.0xa100 +a8000000 OBJ0.0xa104 +00001de7 OBJ0.0xa108 +4003ffff OBJ0.0xa10c +fc01dc23 OBJ0.0xa110 +1a8e0000 OBJ0.0xa114 +00001de7 OBJ0.0xa118 +a8000000 OBJ0.0xa11c +00001df4 OBJ0.0xa120 +40000000 OBJ0.0xa124 +000021e7 OBJ0.0xa128 +a8000000 OBJ0.0xa12c +04411c03 OBJ0.0xa130 +4801c000 OBJ0.0xa134 +40000007 OBJ0.0xa138 +60000020 OBJ0.0xa13c +fc515c43 OBJ0.0xa140 +48000000 OBJ0.0xa144 +00401f25 OBJ0.0xa148 +84000000 OBJ0.0xa14c +9401dc23 OBJ0.0xa150 +1a8ec000 OBJ0.0xa154 +800001e7 OBJ0.0xa158 +40000000 OBJ0.0xa15c +04411c03 OBJ0.0xa160 +4801c000 OBJ0.0xa164 +fc515c43 OBJ0.0xa168 +48000000 OBJ0.0xa16c +00401f25 OBJ0.0xa170 +84000000 OBJ0.0xa174 +fc01dc33 OBJ0.0xa178 +1a8e0000 OBJ0.0xa17c +8001dc23 OBJ0.0xa180 +190ec000 OBJ0.0xa184 +60000007 OBJ0.0xa188 +60000003 OBJ0.0xa18c +000001e7 OBJ0.0xa190 +40000001 OBJ0.0xa194 +b401dc23 OBJ0.0xa198 +190ec000 OBJ0.0xa19c +c00001e7 OBJ0.0xa1a0 +40000000 OBJ0.0xa1a4 +8c01dc23 OBJ0.0xa1a8 +190ec000 OBJ0.0xa1ac +800001e7 OBJ0.0xa1b0 +40000000 OBJ0.0xa1b4 +ac01dc23 OBJ0.0xa1b8 +190ec000 OBJ0.0xa1bc +400001e7 OBJ0.0xa1c0 +40000000 OBJ0.0xa1c4 +c001dc23 OBJ0.0xa1c8 +1a8ec000 OBJ0.0xa1cc +000001f4 OBJ0.0xa1d0 +40000000 OBJ0.0xa1d4 +00000007 OBJ0.0xa1d8 +68000002 OBJ0.0xa1dc +04411c03 OBJ0.0xa1e0 +4801c000 OBJ0.0xa1e4 +a0000007 OBJ0.0xa1e8 +60000001 OBJ0.0xa1ec +fc515c43 OBJ0.0xa1f0 +48000000 OBJ0.0xa1f4 +00401f25 OBJ0.0xa1f8 +84000000 OBJ0.0xa1fc +8001dc23 OBJ0.0xa200 +190ec000 OBJ0.0xa204 +000001e7 OBJ0.0xa208 +40000001 OBJ0.0xa20c +b401dc23 OBJ0.0xa210 +190ec000 OBJ0.0xa214 +c00001e7 OBJ0.0xa218 +40000000 OBJ0.0xa21c +8c01dc23 OBJ0.0xa220 +190ec000 OBJ0.0xa224 +800001e7 OBJ0.0xa228 +40000000 OBJ0.0xa22c +ac01dc23 OBJ0.0xa230 +190ec000 OBJ0.0xa234 +400001e7 OBJ0.0xa238 +40000000 OBJ0.0xa23c +c001dc23 OBJ0.0xa240 +190ec000 OBJ0.0xa244 +000021e7 OBJ0.0xa248 +a8000000 OBJ0.0xa24c +00001df4 OBJ0.0xa250 +40000000 OBJ0.0xa254 +00001de7 OBJ0.0xa258 +4003fffe OBJ0.0xa25c +00001df4 OBJ0.0xa260 +40000000 OBJ0.0xa264 +a801dc23 OBJ0.0xa268 +1a8ec000 OBJ0.0xa26c +80000007 OBJ0.0xa270 +60000002 OBJ0.0xa274 +a00001e7 OBJ0.0xa278 +40000000 OBJ0.0xa27c +04411c03 OBJ0.0xa280 +4801c000 OBJ0.0xa284 +1c71dc04 OBJ0.0xa288 +0c0e0000 OBJ0.0xa28c +fc515c43 OBJ0.0xa290 +48000000 OBJ0.0xa294 +00401f25 OBJ0.0xa298 +84000000 OBJ0.0xa29c +0402ddf2 OBJ0.0xa2a0 +18000000 OBJ0.0xa2a4 +4001dc03 OBJ0.0xa2a8 +4800ffff OBJ0.0xa2ac +60000007 OBJ0.0xa2b0 +60000001 OBJ0.0xa2b4 +1c21dc04 OBJ0.0xa2b8 +1c000000 OBJ0.0xa2bc +2471dc03 OBJ0.0xa2c0 +1a0ec000 OBJ0.0xa2c4 +e00001e7 OBJ0.0xa2c8 +40000000 OBJ0.0xa2cc +04411c03 OBJ0.0xa2d0 +4801c000 OBJ0.0xa2d4 +fc515c43 OBJ0.0xa2d8 +48000000 OBJ0.0xa2dc +00401f25 OBJ0.0xa2e0 +84000000 OBJ0.0xa2e4 +4001dc03 OBJ0.0xa2e8 +4800ffff OBJ0.0xa2ec +1c21dc04 OBJ0.0xa2f0 +1c000000 OBJ0.0xa2f4 +2471dc03 OBJ0.0xa2f8 +198ec000 OBJ0.0xa2fc +200001e7 OBJ0.0xa300 +4003ffff OBJ0.0xa304 +1cf1dc14 OBJ0.0xa308 +0c0e0000 OBJ0.0xa30c +fc02ddf4 OBJ0.0xa310 +28000000 OBJ0.0xa314 +b803dc23 OBJ0.0xa318 +1a8ec000 OBJ0.0xa31c +00000007 OBJ0.0xa320 +60000002 OBJ0.0xa324 +c00005e7 OBJ0.0xa328 +40000001 OBJ0.0xa32c +04411c03 OBJ0.0xa330 +4801c000 OBJ0.0xa334 +fc515c43 OBJ0.0xa338 +48000000 OBJ0.0xa33c +00401f25 OBJ0.0xa340 +84000000 OBJ0.0xa344 +4001dc03 OBJ0.0xa348 +4800ffff OBJ0.0xa34c +1c21dc04 OBJ0.0xa350 +1c000000 OBJ0.0xa354 +2473dc03 OBJ0.0xa358 +1a0ec000 OBJ0.0xa35c +e00005e7 OBJ0.0xa360 +40000000 OBJ0.0xa364 +04411c03 OBJ0.0xa368 +4801c000 OBJ0.0xa36c +fc515c43 OBJ0.0xa370 +48000000 OBJ0.0xa374 +00401f25 OBJ0.0xa378 +84000000 OBJ0.0xa37c +4001dc03 OBJ0.0xa380 +4800ffff OBJ0.0xa384 +1c21dc04 OBJ0.0xa388 +1c000000 OBJ0.0xa38c +2473dc03 OBJ0.0xa390 +198ec000 OBJ0.0xa394 +200005e7 OBJ0.0xa398 +4003ffff OBJ0.0xa39c +b003dc33 OBJ0.0xa3a0 +1a8ec001 OBJ0.0xa3a4 +20000007 OBJ0.0xa3a8 +60000002 OBJ0.0xa3ac +400005e7 OBJ0.0xa3b0 +40000001 OBJ0.0xa3b4 +04411c03 OBJ0.0xa3b8 +4801c000 OBJ0.0xa3bc +9001dde4 OBJ0.0xa3c0 +28004404 OBJ0.0xa3c4 +fc515c43 OBJ0.0xa3c8 +48000000 OBJ0.0xa3cc +00401f25 OBJ0.0xa3d0 +84000000 OBJ0.0xa3d4 +b003dc23 OBJ0.0xa3d8 +1a8ec001 OBJ0.0xa3dc +000005f4 OBJ0.0xa3e0 +40000000 OBJ0.0xa3e4 +04411c03 OBJ0.0xa3e8 +4801c000 OBJ0.0xa3ec +fc515c43 OBJ0.0xa3f0 +48000000 OBJ0.0xa3f4 +00401f25 OBJ0.0xa3f8 +84000000 OBJ0.0xa3fc +0401ddf2 OBJ0.0xa400 +18000000 OBJ0.0xa404 +a003dc23 OBJ0.0xa408 +1a8ec001 OBJ0.0xa40c +600085e7 OBJ0.0xa410 +40000000 OBJ0.0xa414 +04412403 OBJ0.0xa418 +4801c000 OBJ0.0xa41c +fc516443 OBJ0.0xa420 +48000000 OBJ0.0xa424 +00402725 OBJ0.0xa428 +84000000 OBJ0.0xa42c +fc01ddf4 OBJ0.0xa430 +28000000 OBJ0.0xa434 +74031c03 OBJ0.0xa438 +4800fffe OBJ0.0xa43c +00000007 OBJ0.0xa440 +60000014 OBJ0.0xa444 +30231c04 OBJ0.0xa448 +1c000000 OBJ0.0xa44c +04c3dc03 OBJ0.0xa450 +198ec000 OBJ0.0xa454 +c00005e7 OBJ0.0xa458 +40000003 OBJ0.0xa45c +a403dc23 OBJ0.0xa460 +190ec001 OBJ0.0xa464 +800005e7 OBJ0.0xa468 +40000003 OBJ0.0xa46c +bc03dc23 OBJ0.0xa470 +190ec001 OBJ0.0xa474 +400005e7 OBJ0.0xa478 +40000003 OBJ0.0xa47c +d403dc23 OBJ0.0xa480 +190ec001 OBJ0.0xa484 +000005e7 OBJ0.0xa488 +40000003 OBJ0.0xa48c +e003dc23 OBJ0.0xa490 +190ec001 OBJ0.0xa494 +c00005e7 OBJ0.0xa498 +40000002 OBJ0.0xa49c +6003dc23 OBJ0.0xa4a0 +190ec001 OBJ0.0xa4a4 +800005e7 OBJ0.0xa4a8 +40000002 OBJ0.0xa4ac +c003dc23 OBJ0.0xa4b0 +190ec001 OBJ0.0xa4b4 +400005e7 OBJ0.0xa4b8 +40000002 OBJ0.0xa4bc +9403dc23 OBJ0.0xa4c0 +190ec001 OBJ0.0xa4c4 +000005e7 OBJ0.0xa4c8 +40000002 OBJ0.0xa4cc +1403dc23 OBJ0.0xa4d0 +190ec001 OBJ0.0xa4d4 +c00005e7 OBJ0.0xa4d8 +40000001 OBJ0.0xa4dc +9803dc23 OBJ0.0xa4e0 +190ec001 OBJ0.0xa4e4 +800005e7 OBJ0.0xa4e8 +40000001 OBJ0.0xa4ec +9c03dc23 OBJ0.0xa4f0 +190ec001 OBJ0.0xa4f4 +400005e7 OBJ0.0xa4f8 +40000001 OBJ0.0xa4fc +1c03dc23 OBJ0.0xa500 +190ec001 OBJ0.0xa504 +000005e7 OBJ0.0xa508 +40000001 OBJ0.0xa50c +8403dc23 OBJ0.0xa510 +190ec001 OBJ0.0xa514 +c00005e7 OBJ0.0xa518 +40000000 OBJ0.0xa51c +0403dc23 OBJ0.0xa520 +190ec001 OBJ0.0xa524 +800005e7 OBJ0.0xa528 +40000000 OBJ0.0xa52c +cc03dc23 OBJ0.0xa530 +190ec001 OBJ0.0xa534 +400005e7 OBJ0.0xa538 +40000000 OBJ0.0xa53c +4c03dc23 OBJ0.0xa540 +1a8ec001 OBJ0.0xa544 +000005f4 OBJ0.0xa548 +40000000 OBJ0.0xa54c +28b39c03 OBJ0.0xa550 +48000000 OBJ0.0xa554 +7ce3dc03 OBJ0.0xa558 +1a0ec000 OBJ0.0xa55c +000005f4 OBJ0.0xa560 +40000000 OBJ0.0xa564 +10829c03 OBJ0.0xa568 +4801c000 OBJ0.0xa56c +9403dc23 OBJ0.0xa570 +190ec001 OBJ0.0xa574 +00139c85 OBJ0.0xa578 +c8000002 OBJ0.0xa57c +fc92dc43 OBJ0.0xa580 +48000000 OBJ0.0xa584 +20a31c04 OBJ0.0xa588 +20000000 OBJ0.0xa58c +e0000007 OBJ0.0xa590 +60000001 OBJ0.0xa594 +24b35c04 OBJ0.0xa598 +20000000 OBJ0.0xa59c +800005e7 OBJ0.0xa5a0 +40000001 OBJ0.0xa5a4 +1401dc23 OBJ0.0xa5a8 +190ec001 OBJ0.0xa5ac +400001e7 OBJ0.0xa5b0 +40000001 OBJ0.0xa5b4 +9801dc23 OBJ0.0xa5b8 +190ec001 OBJ0.0xa5bc +000001e7 OBJ0.0xa5c0 +40000001 OBJ0.0xa5c4 +9c01dc23 OBJ0.0xa5c8 +190ec001 OBJ0.0xa5cc +c00001e7 OBJ0.0xa5d0 +40000000 OBJ0.0xa5d4 +1c01dc23 OBJ0.0xa5d8 +190ec001 OBJ0.0xa5dc +800001e7 OBJ0.0xa5e0 +40000000 OBJ0.0xa5e4 +8401dc23 OBJ0.0xa5e8 +190ec001 OBJ0.0xa5ec +400001e7 OBJ0.0xa5f0 +40000000 OBJ0.0xa5f4 +0401dc23 OBJ0.0xa5f8 +1a8ec001 OBJ0.0xa5fc +000001f4 OBJ0.0xa600 +40000000 OBJ0.0xa604 +0401ddf2 OBJ0.0xa608 +18000000 OBJ0.0xa60c +4c01dc23 OBJ0.0xa610 +190ec001 OBJ0.0xa614 +cc03dc23 OBJ0.0xa618 +190ec001 OBJ0.0xa61c +c005dc23 OBJ0.0xa620 +190ec001 OBJ0.0xa624 +4405dc04 OBJ0.0xa628 +0c240000 OBJ0.0xa62c +0401c9e2 OBJ0.0xa630 +18000000 OBJ0.0xa634 +fc75dc23 OBJ0.0xa638 +190e0000 OBJ0.0xa63c +200089e7 OBJ0.0xa640 +40000002 OBJ0.0xa644 +1cc26803 OBJ0.0xa648 +6800c000 OBJ0.0xa64c +00122885 OBJ0.0xa650 +c0000002 OBJ0.0xa654 +0402a9e2 OBJ0.0xa658 +18000000 OBJ0.0xa65c +fc9fe903 OBJ0.0xa660 +48010000 OBJ0.0xa664 +5012ea85 OBJ0.0xa668 +c0000000 OBJ0.0xa66c +fff7e843 OBJ0.0xa670 +1a8e0000 OBJ0.0xa674 +20a26803 OBJ0.0xa678 +60000000 OBJ0.0xa67c +10c22803 OBJ0.0xa680 +4801c000 OBJ0.0xa684 +2c92e843 OBJ0.0xa688 +68000000 OBJ0.0xa68c +30832804 OBJ0.0xa690 +20060000 OBJ0.0xa694 +10122a85 OBJ0.0xa698 +c0000001 OBJ0.0xa69c +7c926823 OBJ0.0xa6a0 +7000c004 OBJ0.0xa6a4 +fcd2a843 OBJ0.0xa6a8 +48000000 OBJ0.0xa6ac +5012e885 OBJ0.0xa6b0 +c8000000 OBJ0.0xa6b4 +34a36804 OBJ0.0xa6b8 +20060000 OBJ0.0xa6bc +20922843 OBJ0.0xa6c0 +68000000 OBJ0.0xa6c4 +10122885 OBJ0.0xa6c8 +c8000001 OBJ0.0xa6cc +e0000007 OBJ0.0xa6d0 +60000008 OBJ0.0xa6d4 +400025e7 OBJ0.0xa6d8 +40000003 OBJ0.0xa6dc +00c21fa5 OBJ0.0xa6e0 +84000000 OBJ0.0xa6e4 +0012dc85 OBJ0.0xa6e8 +c0000002 OBJ0.0xa6ec +0403dde2 OBJ0.0xa6f0 +18000000 OBJ0.0xa6f4 +a0000007 OBJ0.0xa6f8 +60000002 OBJ0.0xa6fc +2cf2dc03 OBJ0.0xa700 +60000000 OBJ0.0xa704 +4013de85 OBJ0.0xa708 +c0000001 OBJ0.0xa70c +3cb3dc43 OBJ0.0xa710 +68000000 OBJ0.0xa714 +7cb2dc23 OBJ0.0xa718 +7000c004 OBJ0.0xa71c +4013dc85 OBJ0.0xa720 +c8000001 OBJ0.0xa724 +00829f25 OBJ0.0xa728 +84000000 OBJ0.0xa72c +04821c03 OBJ0.0xa730 +4801c000 OBJ0.0xa734 +fc925c43 OBJ0.0xa738 +48000000 OBJ0.0xa73c +fca1dc23 OBJ0.0xa740 +190e0000 OBJ0.0xa744 +50129e85 OBJ0.0xa748 +c0000001 OBJ0.0xa74c +28b29c43 OBJ0.0xa750 +68000000 OBJ0.0xa754 +50129c85 OBJ0.0xa758 +c8000001 OBJ0.0xa75c +e00001e7 OBJ0.0xa760 +40000000 OBJ0.0xa764 +04821c03 OBJ0.0xa768 +4801c000 OBJ0.0xa76c +0430dc03 OBJ0.0xa770 +4800c000 OBJ0.0xa774 +fc925c43 OBJ0.0xa778 +48000000 OBJ0.0xa77c +1010dc85 OBJ0.0xa780 +c8000002 OBJ0.0xa784 +fc829f25 OBJ0.0xa788 +87ffffff OBJ0.0xa78c +fca1dc23 OBJ0.0xa790 +1a8e0000 OBJ0.0xa794 +200001e7 OBJ0.0xa798 +4003ffff OBJ0.0xa79c +0430dc13 OBJ0.0xa7a0 +4800c000 OBJ0.0xa7a4 +1010dc95 OBJ0.0xa7a8 +c8000002 OBJ0.0xa7ac +000021f4 OBJ0.0xa7b0 +40000000 OBJ0.0xa7b4 +00129c85 OBJ0.0xa7b8 +c0000002 OBJ0.0xa7bc +0402dde2 OBJ0.0xa7c0 +18000000 OBJ0.0xa7c4 +6013de85 OBJ0.0xa7c8 +c0000001 OBJ0.0xa7cc +a3f1dc23 OBJ0.0xa7d0 +190e4404 OBJ0.0xa7d4 +00c21fa5 OBJ0.0xa7d8 +84000000 OBJ0.0xa7dc +28b2dc03 OBJ0.0xa7e0 +60000000 OBJ0.0xa7e4 +7cb29c23 OBJ0.0xa7e8 +7000c004 OBJ0.0xa7ec +3cb3dc43 OBJ0.0xa7f0 +68000000 OBJ0.0xa7f4 +7012de85 OBJ0.0xa7f8 +c0000001 OBJ0.0xa7fc +6013dc85 OBJ0.0xa800 +c8000001 OBJ0.0xa804 +2ca2dc43 OBJ0.0xa808 +68000000 OBJ0.0xa80c +7012dc85 OBJ0.0xa810 +c8000001 OBJ0.0xa814 +e00001e7 OBJ0.0xa818 +40000001 OBJ0.0xa81c +0082df85 OBJ0.0xa820 +84000000 OBJ0.0xa824 +10829c03 OBJ0.0xa828 +4801c000 OBJ0.0xa82c +60000007 OBJ0.0xa830 +60000001 OBJ0.0xa834 +fcb1dc03 OBJ0.0xa838 +190e0000 OBJ0.0xa83c +fc92dc43 OBJ0.0xa840 +48000000 OBJ0.0xa844 +e00001e7 OBJ0.0xa848 +40000000 OBJ0.0xa84c +10a29c03 OBJ0.0xa850 +4801c000 OBJ0.0xa854 +1030dc03 OBJ0.0xa858 +4800c000 OBJ0.0xa85c +fcb2dc43 OBJ0.0xa860 +48000000 OBJ0.0xa864 +1010dc85 OBJ0.0xa868 +c8000002 OBJ0.0xa86c +f0a21f85 OBJ0.0xa870 +87ffffff OBJ0.0xa874 +fc81dc03 OBJ0.0xa878 +1a8e0000 OBJ0.0xa87c +200001e7 OBJ0.0xa880 +4003ffff OBJ0.0xa884 +1030dc13 OBJ0.0xa888 +4800c000 OBJ0.0xa88c +1010dc95 OBJ0.0xa890 +c8000002 OBJ0.0xa894 +0082df45 OBJ0.0xa898 +84000000 OBJ0.0xa89c +08829c03 OBJ0.0xa8a0 +4801c000 OBJ0.0xa8a4 +60000007 OBJ0.0xa8a8 +60000001 OBJ0.0xa8ac +fcb1dc03 OBJ0.0xa8b0 +190e0000 OBJ0.0xa8b4 +fc92dc43 OBJ0.0xa8b8 +48000000 OBJ0.0xa8bc +e00001e7 OBJ0.0xa8c0 +40000000 OBJ0.0xa8c4 +08a29c03 OBJ0.0xa8c8 +4801c000 OBJ0.0xa8cc +0830dc03 OBJ0.0xa8d0 +4800c000 OBJ0.0xa8d4 +fcb2dc43 OBJ0.0xa8d8 +48000000 OBJ0.0xa8dc +1010dc85 OBJ0.0xa8e0 +c8000002 OBJ0.0xa8e4 +f8a21f45 OBJ0.0xa8e8 +87ffffff OBJ0.0xa8ec +fc81dc03 OBJ0.0xa8f0 +1a8e0000 OBJ0.0xa8f4 +200001e7 OBJ0.0xa8f8 +4003ffff OBJ0.0xa8fc +0830dc13 OBJ0.0xa900 +4800c000 OBJ0.0xa904 +1010dc95 OBJ0.0xa908 +c8000002 OBJ0.0xa90c +10721ca3 OBJ0.0xa910 +2019c000 OBJ0.0xa914 +1071dce3 OBJ0.0xa918 +5000c000 OBJ0.0xa91c +04e29c03 OBJ0.0xa920 +4800c000 OBJ0.0xa924 +1cd1dc43 OBJ0.0xa928 +48000000 OBJ0.0xa92c +10821c03 OBJ0.0xa930 +4801c000 OBJ0.0xa934 +00129c85 OBJ0.0xa938 +c8000002 OBJ0.0xa93c +fc725c53 OBJ0.0xa940 +48000000 OBJ0.0xa944 +fc01dc33 OBJ0.0xa948 +1a8e0000 OBJ0.0xa94c +000021e7 OBJ0.0xa950 +a8000000 OBJ0.0xa954 +00001de7 OBJ0.0xa958 +4003ffdd OBJ0.0xa95c +18401d03 OBJ0.0xa960 +48000000 OBJ0.0xa964 +0ca11e03 OBJ0.0xa968 +6000c000 OBJ0.0xa96c +00129c85 OBJ0.0xa970 +c8000001 OBJ0.0xa974 +d0111c85 OBJ0.0xa978 +c8000000 OBJ0.0xa97c +00401c04 OBJ0.0xa980 +c206e006 OBJ0.0xa984 +a4011c03 OBJ0.0xa988 +4800c000 OBJ0.0xa98c +0400dc03 OBJ0.0xa990 +4800c000 OBJ0.0xa994 +20a01c43 OBJ0.0xa998 +5000c000 OBJ0.0xa99c +0041dc03 OBJ0.0xa9a0 +198ec004 OBJ0.0xa9a4 +1010dc85 OBJ0.0xa9a8 +c8000002 OBJ0.0xa9ac +10111c85 OBJ0.0xa9b0 +c8000002 OBJ0.0xa9b4 +20101c85 OBJ0.0xa9b8 +c8000001 OBJ0.0xa9bc +000081e7 OBJ0.0xa9c0 +40000001 OBJ0.0xa9c4 +dc402003 OBJ0.0xa9c8 +4800ffff OBJ0.0xa9cc +140161e2 OBJ0.0xa9d0 +18210842 OBJ0.0xa9d4 +1400e243 OBJ0.0xa9d8 +20000000 OBJ0.0xa9dc +0430e003 OBJ0.0xa9e0 +5800c000 OBJ0.0xa9e4 +14002043 OBJ0.0xa9e8 +20060000 OBJ0.0xa9ec +1c002003 OBJ0.0xa9f0 +5800c000 OBJ0.0xa9f4 +10012063 OBJ0.0xa9f8 +40000000 OBJ0.0xa9fc +10112085 OBJ0.0xaa00 +c8000002 OBJ0.0xaa04 +fc401c03 OBJ0.0xaa08 +4800c003 OBJ0.0xaa0c +00019c03 OBJ0.0xaa10 +6800fffc OBJ0.0xaa14 +8061dc03 OBJ0.0xaa18 +198e4404 OBJ0.0xaa1c +10119c85 OBJ0.0xaa20 +c8000002 OBJ0.0xaa24 +400001e7 OBJ0.0xaa28 +40000000 OBJ0.0xaa2c +fc011de2 OBJ0.0xaa30 +1bffffff OBJ0.0xaa34 +80001de7 OBJ0.0xaa38 +40000044 OBJ0.0xaa3c +0c001c04 OBJ0.0xaa40 +2c000000 OBJ0.0xaa44 +0c00dc04 OBJ0.0xaa48 +2c000000 OBJ0.0xaa4c +40029de4 OBJ0.0xaa50 +28004404 OBJ0.0xaa54 +50025c03 OBJ0.0xaa58 +7000c024 OBJ0.0xaa5c +20311c03 OBJ0.0xaa60 +7000c018 OBJ0.0xaa64 +0070dc24 OBJ0.0xaa68 +49c00000 OBJ0.0xaa6c +c0915c43 OBJ0.0xaa70 +5000c000 OBJ0.0xaa74 +c0901c03 OBJ0.0xaa78 +2009c000 OBJ0.0xaa7c +0c021c03 OBJ0.0xaa80 +78000000 OBJ0.0xaa84 +0001dc04 OBJ0.0xaa88 +2c000000 OBJ0.0xaa8c +17f0dc43 OBJ0.0xaa90 +48000000 OBJ0.0xaa94 +00915ca3 OBJ0.0xaa98 +2015c006 OBJ0.0xaa9c +00929ce3 OBJ0.0xaaa0 +5000c006 OBJ0.0xaaa4 +7c725e03 OBJ0.0xaaa8 +4800c000 OBJ0.0xaaac +7c81de03 OBJ0.0xaab0 +4800c000 OBJ0.0xaab4 +50a29c43 OBJ0.0xaab8 +48004404 OBJ0.0xaabc +20421ce3 OBJ0.0xaac0 +5000c000 OBJ0.0xaac4 +20411ca3 OBJ0.0xaac8 +200bc000 OBJ0.0xaacc +2475dc03 OBJ0.0xaad0 +1a8e0000 OBJ0.0xaad4 +7401dc03 OBJ0.0xaad8 +5800c000 OBJ0.0xaadc +20a15c43 OBJ0.0xaae0 +48000000 OBJ0.0xaae4 +60421c03 OBJ0.0xaae8 +4801c000 OBJ0.0xaaec +1c30dc63 OBJ0.0xaaf0 +40000000 OBJ0.0xaaf4 +40025de4 OBJ0.0xaaf8 +28004404 OBJ0.0xaafc +00821c02 OBJ0.0xab00 +3bfc0000 OBJ0.0xab04 +17f1dc43 OBJ0.0xab08 +48000000 OBJ0.0xab0c +20031c03 OBJ0.0xab10 +2013c000 OBJ0.0xab14 +00701c24 OBJ0.0xab18 +49c00000 OBJ0.0xab1c +0081dc03 OBJ0.0xab20 +190e4000 OBJ0.0xab24 +fc73dc03 OBJ0.0xab28 +190e0000 OBJ0.0xab2c +50335c43 OBJ0.0xab30 +48004404 OBJ0.0xab34 +00001c03 OBJ0.0xab38 +78000000 OBJ0.0xab3c +0401dc04 OBJ0.0xab40 +0c0e0000 OBJ0.0xab44 +30125e85 OBJ0.0xab48 +c0000001 OBJ0.0xab4c +60cfeba5 OBJ0.0xab50 +94000000 OBJ0.0xab54 +7c001e03 OBJ0.0xab58 +4800c000 OBJ0.0xab5c +fc01dde4 OBJ0.0xab60 +28000000 OBJ0.0xab64 +e0000007 OBJ0.0xab68 +60000001 OBJ0.0xab6c +800001e7 OBJ0.0xab70 +40000000 OBJ0.0xab74 +60419e05 OBJ0.0xab78 +547e5000 OBJ0.0xab7c +3012dc85 OBJ0.0xab80 +c8000001 OBJ0.0xab84 +60401ca5 OBJ0.0xab88 +9c000000 OBJ0.0xab8c +20001de7 OBJ0.0xab90 +40000001 OBJ0.0xab94 +60429c85 OBJ0.0xab98 +a0000000 OBJ0.0xab9c +1cf3dc04 OBJ0.0xaba0 +0c0e0000 OBJ0.0xaba4 +70424185 OBJ0.0xaba8 +a0000000 OBJ0.0xabac +18a0c403 OBJ0.0xabb0 +48010000 OBJ0.0xabb4 +30125c85 OBJ0.0xabb8 +c8000001 OBJ0.0xabbc +1c920443 OBJ0.0xabc0 +48000000 OBJ0.0xabc4 +70420485 OBJ0.0xabc8 +e8000000 OBJ0.0xabcc +6040c085 OBJ0.0xabd0 +e8000000 OBJ0.0xabd4 +e00025e7 OBJ0.0xabd8 +4003fffe OBJ0.0xabdc +00001df4 OBJ0.0xabe0 +40000000 OBJ0.0xabe4 +60c19fa5 OBJ0.0xabe8 +84000000 OBJ0.0xabec +0000dc04 OBJ0.0xabf0 +2c000000 OBJ0.0xabf4 +00000007 OBJ0.0xabf8 +60000008 OBJ0.0xabfc +7c30de03 OBJ0.0xac00 +4800c000 OBJ0.0xac04 +0c01dc03 OBJ0.0xac08 +1a8e0000 OBJ0.0xac0c +f011dc85 OBJ0.0xac10 +c8000000 OBJ0.0xac14 +e0119c85 OBJ0.0xac18 +c8000000 OBJ0.0xac1c +000001e7 OBJ0.0xac20 +40000007 OBJ0.0xac24 +806fde03 OBJ0.0xac28 +48014404 OBJ0.0xac2c +a0000007 OBJ0.0xac30 +60000006 OBJ0.0xac34 +1ff1dc43 OBJ0.0xac38 +188e0000 OBJ0.0xac3c +a00001e7 OBJ0.0xac40 +40000005 OBJ0.0xac44 +40001de4 OBJ0.0xac48 +28004404 OBJ0.0xac4c +90125e85 OBJ0.0xac50 +c0000001 OBJ0.0xac54 +60000007 OBJ0.0xac58 +60000002 OBJ0.0xac5c +40011c03 OBJ0.0xac60 +4801c000 OBJ0.0xac64 +00401c02 OBJ0.0xac68 +3bfc0000 OBJ0.0xac6c +53f15c43 OBJ0.0xac70 +48004404 OBJ0.0xac74 +0001dc03 OBJ0.0xac78 +190e4000 OBJ0.0xac7c +fc53dc03 OBJ0.0xac80 +190e0000 OBJ0.0xac84 +0401dc04 OBJ0.0xac88 +0c0e0000 OBJ0.0xac8c +600001e7 OBJ0.0xac90 +40000000 OBJ0.0xac94 +00419e05 OBJ0.0xac98 +547e4000 OBJ0.0xac9c +00401ca5 OBJ0.0xaca0 +9c000000 OBJ0.0xaca4 +00001de7 OBJ0.0xaca8 +40000001 OBJ0.0xacac +00421c85 OBJ0.0xacb0 +a0000000 OBJ0.0xacb4 +1cf3dc04 OBJ0.0xacb8 +0c0e0000 OBJ0.0xacbc +10424185 OBJ0.0xacc0 +a0000000 OBJ0.0xacc4 +18800403 OBJ0.0xacc8 +48010000 OBJ0.0xaccc +1c90c443 OBJ0.0xacd0 +48000000 OBJ0.0xacd4 +1040c485 OBJ0.0xacd8 +e8000000 OBJ0.0xacdc +00400085 OBJ0.0xace0 +e8000000 OBJ0.0xace4 +000025e7 OBJ0.0xace8 +4003ffff OBJ0.0xacec +00001df4 OBJ0.0xacf0 +40000000 OBJ0.0xacf4 +90125c85 OBJ0.0xacf8 +c8000001 OBJ0.0xacfc +80121c85 OBJ0.0xad00 +c8000001 OBJ0.0xad04 +40001de2 OBJ0.0xad08 +1800009c OBJ0.0xad0c +00000007 OBJ0.0xad10 +68000003 OBJ0.0xad14 +60039de4 OBJ0.0xad18 +28004404 OBJ0.0xad1c +7003dde4 OBJ0.0xad20 +28004404 OBJ0.0xad24 +fc001c03 OBJ0.0xad28 +4800ffff OBJ0.0xad2c +00e11fa5 OBJ0.0xad30 +84000000 OBJ0.0xad34 +fc01dc03 OBJ0.0xad38 +190e0000 OBJ0.0xad3c +108fdd03 OBJ0.0xad40 +48010000 OBJ0.0xad44 +1491dc43 OBJ0.0xad48 +18a00000 OBJ0.0xad4c +600021e7 OBJ0.0xad50 +40000000 OBJ0.0xad54 +fc021de2 OBJ0.0xad58 +1bffffff OBJ0.0xad5c +fc025de2 OBJ0.0xad60 +1bffffff OBJ0.0xad64 +00001de7 OBJ0.0xad68 +a8000000 OBJ0.0xad6c +1080dd03 OBJ0.0xad70 +48010000 OBJ0.0xad74 +14911d43 OBJ0.0xad78 +48000000 OBJ0.0xad7c +0c60dc03 OBJ0.0xad80 +48010000 OBJ0.0xad84 +10711c43 OBJ0.0xad88 +48000000 OBJ0.0xad8c +803fde03 OBJ0.0xad90 +48014404 OBJ0.0xad94 +13f1dc43 OBJ0.0xad98 +188e0000 OBJ0.0xad9c +000021e7 OBJ0.0xada0 +a8000000 OBJ0.0xada4 +a0001de7 OBJ0.0xada8 +4003fffd OBJ0.0xadac +fc011de4 OBJ0.0xadb0 +28000000 OBJ0.0xadb4 +fc015de4 OBJ0.0xadb8 +28000000 OBJ0.0xadbc +f8021de2 OBJ0.0xadc0 +1bffffff OBJ0.0xadc4 +fc025de4 OBJ0.0xadc8 +28000000 OBJ0.0xadcc +80111cb5 OBJ0.0xadd0 +c8000001 OBJ0.0xadd4 +00001df4 OBJ0.0xadd8 +40000000 OBJ0.0xaddc +60c21fb5 OBJ0.0xade0 +94000000 OBJ0.0xade4 +fc011de4 OBJ0.0xade8 +28000000 OBJ0.0xadec +fc015de4 OBJ0.0xadf0 +28000000 OBJ0.0xadf4 +80111cb5 OBJ0.0xadf8 +c8000001 OBJ0.0xadfc +60c11fa5 OBJ0.0xae00 +84000000 OBJ0.0xae04 +f84fdd03 OBJ0.0xae08 +4801ffff OBJ0.0xae0c +fc51dc43 OBJ0.0xae10 +1a8effff OBJ0.0xae14 +400001e7 OBJ0.0xae18 +40000000 OBJ0.0xae1c +f8011de2 OBJ0.0xae20 +1bffffff OBJ0.0xae24 +c0001de7 OBJ0.0xae28 +40000034 OBJ0.0xae2c +fc4fdd03 OBJ0.0xae30 +4801ffff OBJ0.0xae34 +c0000007 OBJ0.0xae38 +6000001f OBJ0.0xae3c +fc51dc43 OBJ0.0xae40 +1a8effff OBJ0.0xae44 +1c001c04 OBJ0.0xae48 +080e0000 OBJ0.0xae4c +10101c85 OBJ0.0xae50 +c8000000 OBJ0.0xae54 +200021e7 OBJ0.0xae58 +4000001f OBJ0.0xae5c +30101e85 OBJ0.0xae60 +c0000001 OBJ0.0xae64 +10a21c03 OBJ0.0xae68 +48010000 OBJ0.0xae6c +fc01dde4 OBJ0.0xae70 +28000000 OBJ0.0xae74 +80019de4 OBJ0.0xae78 +28004404 OBJ0.0xae7c +a0121c85 OBJ0.0xae80 +c8000000 OBJ0.0xae84 +20011de4 OBJ0.0xae88 +28000000 OBJ0.0xae8c +14001c43 OBJ0.0xae90 +48000000 OBJ0.0xae94 +b0101c85 OBJ0.0xae98 +c8000000 OBJ0.0xae9c +00015de4 OBJ0.0xaea0 +28000000 OBJ0.0xaea4 +00010007 OBJ0.0xaea8 +10000208 OBJ0.0xaeac +d0101e85 OBJ0.0xaeb0 +c0000000 OBJ0.0xaeb4 +20411c03 OBJ0.0xaeb8 +48014404 OBJ0.0xaebc +2010de85 OBJ0.0xaec0 +c0000001 OBJ0.0xaec4 +3051dc43 OBJ0.0xaec8 +48004404 OBJ0.0xaecc +c0111c85 OBJ0.0xaed0 +c8000000 OBJ0.0xaed4 +a0015c03 OBJ0.0xaed8 +4801c000 OBJ0.0xaedc +d011dc85 OBJ0.0xaee0 +c8000000 OBJ0.0xaee4 +fc319c43 OBJ0.0xaee8 +48000000 OBJ0.0xaeec +00401c03 OBJ0.0xaef0 +48010000 OBJ0.0xaef4 +0c70dc43 OBJ0.0xaef8 +48000000 OBJ0.0xaefc +005fdd03 OBJ0.0xaf00 +4801c004 OBJ0.0xaf04 +fc61dc63 OBJ0.0xaf08 +198e0000 OBJ0.0xaf0c +a0021c03 OBJ0.0xaf10 +4801c000 OBJ0.0xaf14 +80001de4 OBJ0.0xaf18 +28004404 OBJ0.0xaf1c +fc325c43 OBJ0.0xaf20 +48000000 OBJ0.0xaf24 +a0419c03 OBJ0.0xaf28 +4801c000 OBJ0.0xaf2c +fc70dc43 OBJ0.0xaf30 +48000000 OBJ0.0xaf34 +20029c03 OBJ0.0xaf38 +48014404 OBJ0.0xaf3c +20119c85 OBJ0.0xaf40 +c8000001 OBJ0.0xaf44 +3010dc85 OBJ0.0xaf48 +c8000001 OBJ0.0xaf4c +33f01c43 OBJ0.0xaf50 +48004404 OBJ0.0xaf54 +c00081e7 OBJ0.0xaf58 +40000000 OBJ0.0xaf5c +20afe103 OBJ0.0xaf60 +48010000 OBJ0.0xaf64 +2403e043 OBJ0.0xaf68 +198e0000 OBJ0.0xaf6c +2080e004 OBJ0.0xaf70 +20124404 OBJ0.0xaf74 +30912004 OBJ0.0xaf78 +20124404 OBJ0.0xaf7c +20322003 OBJ0.0xaf80 +4801c000 OBJ0.0xaf84 +fc426043 OBJ0.0xaf88 +48000000 OBJ0.0xaf8c +9010de85 OBJ0.0xaf90 +c0000000 OBJ0.0xaf94 +c012dc03 OBJ0.0xaf98 +4800c001 OBJ0.0xaf9c +fc811c03 OBJ0.0xafa0 +6800c003 OBJ0.0xafa4 +fc4fdd03 OBJ0.0xafa8 +48010000 OBJ0.0xafac +fff1dc43 OBJ0.0xafb0 +1a8e0000 OBJ0.0xafb4 +400081e7 OBJ0.0xafb8 +40000001 OBJ0.0xafbc +10b1a003 OBJ0.0xafc0 +48014000 OBJ0.0xafc4 +fff1e043 OBJ0.0xafc8 +48000000 OBJ0.0xafcc +20afe103 OBJ0.0xafd0 +48010000 OBJ0.0xafd4 +006123a5 OBJ0.0xafd8 +84000000 OBJ0.0xafdc +2403e043 OBJ0.0xafe0 +198e0000 OBJ0.0xafe4 +2081a004 OBJ0.0xafe8 +20124404 OBJ0.0xafec +3091e004 OBJ0.0xaff0 +20124404 OBJ0.0xaff4 +20622003 OBJ0.0xaff8 +4801c000 OBJ0.0xaffc +fc726043 OBJ0.0xb000 +48000000 OBJ0.0xb004 +006123a5 OBJ0.0xb008 +94000000 OBJ0.0xb00c +00211f25 OBJ0.0xb010 +84000000 OBJ0.0xb014 +04821c03 OBJ0.0xb018 +4801c000 OBJ0.0xb01c +fc925c43 OBJ0.0xb020 +48000000 OBJ0.0xb024 +04209c03 OBJ0.0xb028 +4801c000 OBJ0.0xb02c +fc30dc43 OBJ0.0xb030 +48000000 OBJ0.0xb034 +fc811f25 OBJ0.0xb038 +97ffffff OBJ0.0xb03c +fc215f25 OBJ0.0xb040 +87ffffff OBJ0.0xb044 +fc51dc23 OBJ0.0xb048 +1a8e0000 OBJ0.0xb04c +200001e7 OBJ0.0xb050 +4003fffd OBJ0.0xb054 +0010dc85 OBJ0.0xb058 +c0000001 OBJ0.0xb05c +80000007 OBJ0.0xb060 +60000014 OBJ0.0xb064 +fc31dc03 OBJ0.0xb068 +190e0000 OBJ0.0xb06c +200001e7 OBJ0.0xb070 +40000014 OBJ0.0xb074 +6010de85 OBJ0.0xb078 +c0000001 OBJ0.0xb07c +40115c85 OBJ0.0xb080 +c0000001 OBJ0.0xb084 +70111e85 OBJ0.0xb088 +c0000001 OBJ0.0xb08c +50119c85 OBJ0.0xb090 +c0000001 OBJ0.0xb094 +14315c43 OBJ0.0xb098 +68000000 OBJ0.0xb09c +fc00dde4 OBJ0.0xb0a0 +28000000 OBJ0.0xb0a4 +18411c43 OBJ0.0xb0a8 +68000000 OBJ0.0xb0ac +2010dc85 OBJ0.0xb0b0 +c8000000 OBJ0.0xb0b4 +60111ca5 OBJ0.0xb0b8 +c8000000 OBJ0.0xb0bc +04011de2 OBJ0.0xb0c0 +18000000 OBJ0.0xb0c4 +50115c85 OBJ0.0xb0c8 +c0000000 OBJ0.0xb0cc +10119c85 OBJ0.0xb0d0 +c0000001 OBJ0.0xb0d4 +0c40dc03 OBJ0.0xb0d8 +60000000 OBJ0.0xb0dc +7c331c23 OBJ0.0xb0e0 +7000c004 OBJ0.0xb0e4 +14311c03 OBJ0.0xb0e8 +68000000 OBJ0.0xb0ec +fc4fdd03 OBJ0.0xb0f0 +48010000 OBJ0.0xb0f4 +18c11c03 OBJ0.0xb0f8 +68000000 OBJ0.0xb0fc +fc41dc43 OBJ0.0xb100 +190e0000 OBJ0.0xb104 +e00081e7 OBJ0.0xb108 +40000001 OBJ0.0xb10c +a012a2a5 OBJ0.0xb110 +c0000001 OBJ0.0xb114 +1ca12003 OBJ0.0xb118 +6800c000 OBJ0.0xb11c +fc4fe103 OBJ0.0xb120 +48010000 OBJ0.0xb124 +fff3e043 OBJ0.0xb128 +1a8e0000 OBJ0.0xb12c +10a12003 OBJ0.0xb130 +4801c000 OBJ0.0xb134 +fcb16043 OBJ0.0xb138 +48000000 OBJ0.0xb13c +28412004 OBJ0.0xb140 +20020000 OBJ0.0xb144 +2c516004 OBJ0.0xb148 +20020000 OBJ0.0xb14c +2042a003 OBJ0.0xb150 +4801c000 OBJ0.0xb154 +0041a3a5 OBJ0.0xb158 +84000000 OBJ0.0xb15c +fc52e043 OBJ0.0xb160 +48000000 OBJ0.0xb164 +a012a085 OBJ0.0xb168 +c8000001 OBJ0.0xb16c +b012e085 OBJ0.0xb170 +c8000001 OBJ0.0xb174 +6011a0a5 OBJ0.0xb178 +c8000001 OBJ0.0xb17c +2000a1e7 OBJ0.0xb180 +40000001 OBJ0.0xb184 +a01282a5 OBJ0.0xb188 +c0000001 OBJ0.0xb18c +fc01c1e4 OBJ0.0xb190 +28000000 OBJ0.0xb194 +7011c085 OBJ0.0xb198 +c8000001 OBJ0.0xb19c +00a18385 OBJ0.0xb1a0 +84000000 OBJ0.0xb1a4 +10a28003 OBJ0.0xb1a8 +4801c000 OBJ0.0xb1ac +fcb2c043 OBJ0.0xb1b0 +48000000 OBJ0.0xb1b4 +a0128085 OBJ0.0xb1b8 +c8000001 OBJ0.0xb1bc +b012c085 OBJ0.0xb1c0 +c8000001 OBJ0.0xb1c4 +60118085 OBJ0.0xb1c8 +c8000001 OBJ0.0xb1cc +70111c85 OBJ0.0xb1d0 +c0000000 OBJ0.0xb1d4 +60115c85 OBJ0.0xb1d8 +c0000000 OBJ0.0xb1dc +40000007 OBJ0.0xb1e0 +6000000a OBJ0.0xb1e4 +10311c03 OBJ0.0xb1e8 +68000000 OBJ0.0xb1ec +fc4fdd03 OBJ0.0xb1f0 +48010000 OBJ0.0xb1f4 +14c11c03 OBJ0.0xb1f8 +68000000 OBJ0.0xb1fc +fc41dc43 OBJ0.0xb200 +190e0000 OBJ0.0xb204 +800001e7 OBJ0.0xb208 +40000009 OBJ0.0xb20c +40129ca5 OBJ0.0xb210 +c0000001 OBJ0.0xb214 +c0111ca5 OBJ0.0xb218 +c0000000 OBJ0.0xb21c +2830dc03 OBJ0.0xb220 +68000000 OBJ0.0xb224 +fc3fdd03 OBJ0.0xb228 +48010000 OBJ0.0xb22c +2cc0dc03 OBJ0.0xb230 +68000000 OBJ0.0xb234 +fc33dc43 OBJ0.0xb238 +190e0000 OBJ0.0xb23c +204fdd03 OBJ0.0xb240 +48010000 OBJ0.0xb244 +0400e5e2 OBJ0.0xb248 +18000000 OBJ0.0xb24c +2451dc43 OBJ0.0xb250 +1a0e0000 OBJ0.0xb254 +10811d03 OBJ0.0xb258 +48010000 OBJ0.0xb25c +fc0325e4 OBJ0.0xb260 +28000000 OBJ0.0xb264 +14915d43 OBJ0.0xb268 +48000000 OBJ0.0xb26c +80410003 OBJ0.0xb270 +48014404 OBJ0.0xb274 +60111ca5 OBJ0.0xb278 +c8000001 OBJ0.0xb27c +fc514043 OBJ0.0xb280 +48000000 OBJ0.0xb284 +70115c85 OBJ0.0xb288 +c8000001 OBJ0.0xb28c +8000a5e7 OBJ0.0xb290 +40000000 OBJ0.0xb294 +a3f1c423 OBJ0.0xb298 +1a8e4404 OBJ0.0xb29c +1000c5e2 OBJ0.0xb2a0 +18000000 OBJ0.0xb2a4 +fff30404 OBJ0.0xb2a8 +20000000 OBJ0.0xb2ac +0830c404 OBJ0.0xb2b0 +2000c000 OBJ0.0xb2b4 +fc3fdd03 OBJ0.0xb2b8 +48010000 OBJ0.0xb2bc +c013dc03 OBJ0.0xb2c0 +4800c001 OBJ0.0xb2c4 +fcc1dc43 OBJ0.0xb2c8 +1a0e0000 OBJ0.0xb2cc +043fdd03 OBJ0.0xb2d0 +4801c000 OBJ0.0xb2d4 +fcc3dc43 OBJ0.0xb2d8 +190e0000 OBJ0.0xb2dc +18009de4 OBJ0.0xb2e0 +28000000 OBJ0.0xb2e4 +40000007 OBJ0.0xb2e8 +60000004 OBJ0.0xb2ec +80109c85 OBJ0.0xb2f0 +c8000000 OBJ0.0xb2f4 +1c009de4 OBJ0.0xb2f8 +28000000 OBJ0.0xb2fc +90109c85 OBJ0.0xb300 +c8000000 OBJ0.0xb304 +a00021e7 OBJ0.0xb308 +40000003 OBJ0.0xb30c +fc035de4 OBJ0.0xb310 +28000000 OBJ0.0xb314 +fc039de4 OBJ0.0xb318 +28000000 OBJ0.0xb31c +fc811c03 OBJ0.0xb320 +6800c003 OBJ0.0xb324 +fc4fdd03 OBJ0.0xb328 +48010000 OBJ0.0xb32c +fff5dc43 OBJ0.0xb330 +1a8e0000 OBJ0.0xb334 +800089e7 OBJ0.0xb338 +40000001 OBJ0.0xb33c +10f2a803 OBJ0.0xb340 +48014000 OBJ0.0xb344 +fff2e843 OBJ0.0xb348 +48000000 OBJ0.0xb34c +00a12ba5 OBJ0.0xb350 +84000000 OBJ0.0xb354 +8002a9e4 OBJ0.0xb358 +28004404 OBJ0.0xb35c +20a2a803 OBJ0.0xb360 +48004404 OBJ0.0xb364 +20afe903 OBJ0.0xb368 +48010000 OBJ0.0xb36c +2407e843 OBJ0.0xb370 +198e0000 OBJ0.0xb374 +2082a804 OBJ0.0xb378 +20164404 OBJ0.0xb37c +3092e804 OBJ0.0xb380 +20164404 OBJ0.0xb384 +20a22803 OBJ0.0xb388 +4801c000 OBJ0.0xb38c +fcb26843 OBJ0.0xb390 +48000000 OBJ0.0xb394 +00a12ba5 OBJ0.0xb398 +94000000 OBJ0.0xb39c +04619c03 OBJ0.0xb3a0 +4801c000 OBJ0.0xb3a4 +fc71dc43 OBJ0.0xb3a8 +48000000 OBJ0.0xb3ac +04821c03 OBJ0.0xb3b0 +4801c000 OBJ0.0xb3b4 +fc611f25 OBJ0.0xb3b8 +87ffffff OBJ0.0xb3bc +fc925c43 OBJ0.0xb3c0 +48000000 OBJ0.0xb3c4 +04d35c03 OBJ0.0xb3c8 +4801c000 OBJ0.0xb3cc +fce39c43 OBJ0.0xb3d0 +48000000 OBJ0.0xb3d4 +0cdfdd03 OBJ0.0xb3d8 +48010000 OBJ0.0xb3dc +30e5dc43 OBJ0.0xb3e0 +1a8e0000 OBJ0.0xb3e4 +fc811f25 OBJ0.0xb3e8 +97ffffff OBJ0.0xb3ec +a00009e7 OBJ0.0xb3f0 +4003fffc OBJ0.0xb3f4 +00001df4 OBJ0.0xb3f8 +40000000 OBJ0.0xb3fc +80000007 OBJ0.0xb400 +60000001 OBJ0.0xb404 +600025e7 OBJ0.0xb408 +40000000 OBJ0.0xb40c +80111ea5 OBJ0.0xb410 +c0000000 OBJ0.0xb414 +00411f25 OBJ0.0xb418 +84000000 OBJ0.0xb41c +fc45dc33 OBJ0.0xb420 +190e0000 OBJ0.0xb424 +083fdd03 OBJ0.0xb428 +4801c000 OBJ0.0xb42c +80129ea5 OBJ0.0xb430 +c0000000 OBJ0.0xb434 +fcc7dc43 OBJ0.0xb438 +1a8e0000 OBJ0.0xb43c +00a12f45 OBJ0.0xb440 +84000000 OBJ0.0xb444 +00a14f85 OBJ0.0xb448 +84000000 OBJ0.0xb44c +fc45ec03 OBJ0.0xb450 +190e0000 OBJ0.0xb454 +fc55cc03 OBJ0.0xb458 +190e0000 OBJ0.0xb45c +00001df4 OBJ0.0xb460 +40000000 OBJ0.0xb464 +c00029e7 OBJ0.0xb468 +4003fff9 OBJ0.0xb46c +00001df4 OBJ0.0xb470 +40000000 OBJ0.0xb474 +2010de85 OBJ0.0xb478 +c0000001 OBJ0.0xb47c +fc311c03 OBJ0.0xb480 +6800c003 OBJ0.0xb484 +fc4fdd03 OBJ0.0xb488 +48010000 OBJ0.0xb48c +fff1dc43 OBJ0.0xb490 +1a8e0000 OBJ0.0xb494 +e00081e7 OBJ0.0xb498 +40000001 OBJ0.0xb49c +c0112003 OBJ0.0xb4a0 +4800c001 OBJ0.0xb4a4 +8002a1e4 OBJ0.0xb4a8 +28004404 OBJ0.0xb4ac +3012e285 OBJ0.0xb4b0 +c0000001 OBJ0.0xb4b4 +1041a003 OBJ0.0xb4b8 +48014000 OBJ0.0xb4bc +20a2a003 OBJ0.0xb4c0 +48004404 OBJ0.0xb4c4 +fff1e043 OBJ0.0xb4c8 +48000000 OBJ0.0xb4cc +0cafe103 OBJ0.0xb4d0 +48010000 OBJ0.0xb4d4 +006123a5 OBJ0.0xb4d8 +84000000 OBJ0.0xb4dc +2c03e043 OBJ0.0xb4e0 +198e0000 OBJ0.0xb4e4 +2031a004 OBJ0.0xb4e8 +20124404 OBJ0.0xb4ec +30b1e004 OBJ0.0xb4f0 +20124404 OBJ0.0xb4f4 +2060e003 OBJ0.0xb4f8 +4801c000 OBJ0.0xb4fc +fc72a043 OBJ0.0xb500 +48000000 OBJ0.0xb504 +3012a085 OBJ0.0xb508 +c8000001 OBJ0.0xb50c +006123a5 OBJ0.0xb510 +94000000 OBJ0.0xb514 +20129e85 OBJ0.0xb518 +c0000000 OBJ0.0xb51c +3011de85 OBJ0.0xb520 +c0000001 OBJ0.0xb524 +0012dc85 OBJ0.0xb528 +c0000001 OBJ0.0xb52c +20319c03 OBJ0.0xb530 +4801c000 OBJ0.0xb534 +60111e85 OBJ0.0xb538 +c0000001 OBJ0.0xb53c +70115e85 OBJ0.0xb540 +c0000001 OBJ0.0xb544 +04a0dc03 OBJ0.0xb548 +4800c000 OBJ0.0xb54c +fc71dc43 OBJ0.0xb550 +48000000 OBJ0.0xb554 +2c31dc03 OBJ0.0xb558 +1a8e0000 OBJ0.0xb55c +2010dc85 OBJ0.0xb560 +c8000000 OBJ0.0xb564 +20119ca5 OBJ0.0xb568 +c8000001 OBJ0.0xb56c +e0611fa5 OBJ0.0xb570 +97ffffff OBJ0.0xb574 +000001e7 OBJ0.0xb578 +4003ffed OBJ0.0xb57c +00001df4 OBJ0.0xb580 +40000000 OBJ0.0xb584 +e0101c03 OBJ0.0xb588 +4800c001 OBJ0.0xb58c +c0111ea5 OBJ0.0xb590 +c0000000 OBJ0.0xb594 +10019c03 OBJ0.0xb598 +48014000 OBJ0.0xb59c +fff1dc43 OBJ0.0xb5a0 +48000000 OBJ0.0xb5a4 +00621fa5 OBJ0.0xb5a8 +84000000 OBJ0.0xb5ac +00421fa5 OBJ0.0xb5b0 +94000000 OBJ0.0xb5b4 +20629fa5 OBJ0.0xb5b8 +84000000 OBJ0.0xb5bc +20429fa5 OBJ0.0xb5c0 +94000000 OBJ0.0xb5c4 +40621fa5 OBJ0.0xb5c8 +84000000 OBJ0.0xb5cc +40421fa5 OBJ0.0xb5d0 +94000000 OBJ0.0xb5d4 +60629fa5 OBJ0.0xb5d8 +84000000 OBJ0.0xb5dc +60429fa5 OBJ0.0xb5e0 +94000000 OBJ0.0xb5e4 +80621fa5 OBJ0.0xb5e8 +84000000 OBJ0.0xb5ec +80421fa5 OBJ0.0xb5f0 +94000000 OBJ0.0xb5f4 +00001c05 OBJ0.0xb5f8 +e0000000 OBJ0.0xb5fc +00001c45 OBJ0.0xb600 +e0000000 OBJ0.0xb604 +a0121ea5 OBJ0.0xb608 +c0000000 OBJ0.0xb60c +60421fa5 OBJ0.0xb610 +94000000 OBJ0.0xb614 +00001c05 OBJ0.0xb618 +e0000000 OBJ0.0xb61c +00001c45 OBJ0.0xb620 +e0000000 OBJ0.0xb624 +00001df4 OBJ0.0xb628 +40000000 OBJ0.0xb62c +00701c24 OBJ0.0xb630 +49c00000 OBJ0.0xb634 +0000dc04 OBJ0.0xb638 +2c000000 OBJ0.0xb63c +e0000007 OBJ0.0xb640 +60000013 OBJ0.0xb644 +00001c03 OBJ0.0xb648 +78000000 OBJ0.0xb64c +7c30de03 OBJ0.0xb650 +4800c000 OBJ0.0xb654 +7c001e03 OBJ0.0xb658 +4800c000 OBJ0.0xb65c +0c01dc03 OBJ0.0xb660 +1a8e0000 OBJ0.0xb664 +200001e7 OBJ0.0xb668 +40000013 OBJ0.0xb66c +40031de4 OBJ0.0xb670 +28004404 OBJ0.0xb674 +50035de4 OBJ0.0xb678 +28004404 OBJ0.0xb67c +80121ea5 OBJ0.0xb680 +c0000001 OBJ0.0xb684 +e0139ea5 OBJ0.0xb688 +c0000000 OBJ0.0xb68c +00c11fa5 OBJ0.0xb690 +84000000 OBJ0.0xb694 +3011dc85 OBJ0.0xb698 +c0000000 OBJ0.0xb69c +80000007 OBJ0.0xb6a0 +68000004 OBJ0.0xb6a4 +20e29c03 OBJ0.0xb6a8 +48010000 OBJ0.0xb6ac +40021de4 OBJ0.0xb6b0 +28004404 OBJ0.0xb6b4 +24f2dc43 OBJ0.0xb6b8 +48000000 OBJ0.0xb6bc +50025de4 OBJ0.0xb6c0 +28004404 OBJ0.0xb6c4 +10afdd03 OBJ0.0xb6c8 +48010000 OBJ0.0xb6cc +14b1dc43 OBJ0.0xb6d0 +198e0000 OBJ0.0xb6d4 +000001e7 OBJ0.0xb6d8 +a8000000 OBJ0.0xb6dc +00801c02 OBJ0.0xb6e0 +3bfc0000 OBJ0.0xb6e4 +fc93dc03 OBJ0.0xb6e8 +190e0000 OBJ0.0xb6ec +0001dc03 OBJ0.0xb6f0 +190e4000 OBJ0.0xb6f4 +0401dc04 OBJ0.0xb6f8 +0c0e0000 OBJ0.0xb6fc +600001e7 OBJ0.0xb700 +40000000 OBJ0.0xb704 +00811f25 OBJ0.0xb708 +54143000 OBJ0.0xb70c +00801ca5 OBJ0.0xb710 +9c000000 OBJ0.0xb714 +80001de7 OBJ0.0xb718 +40000001 OBJ0.0xb71c +60000007 OBJ0.0xb720 +60000001 OBJ0.0xb724 +00819c85 OBJ0.0xb728 +a0000000 OBJ0.0xb72c +1cf3dc04 OBJ0.0xb730 +0c0e0000 OBJ0.0xb734 +1081c185 OBJ0.0xb738 +a0000000 OBJ0.0xb73c +106fc503 OBJ0.0xb740 +48010000 OBJ0.0xb744 +1475c443 OBJ0.0xb748 +190e0000 OBJ0.0xb74c +1cb0c404 OBJ0.0xb750 +20040000 OBJ0.0xb754 +18a00404 OBJ0.0xb758 +20040000 OBJ0.0xb75c +1080c485 OBJ0.0xb760 +e8000000 OBJ0.0xb764 +00800085 OBJ0.0xb768 +e8000000 OBJ0.0xb76c +c00025e7 OBJ0.0xb770 +4003fffe OBJ0.0xb774 +00001df4 OBJ0.0xb778 +40000000 OBJ0.0xb77c +106fdd03 OBJ0.0xb780 +48010000 OBJ0.0xb784 +1471dc43 OBJ0.0xb788 +190e0000 OBJ0.0xb78c +000001e7 OBJ0.0xb790 +a8000000 OBJ0.0xb794 +18afdd03 OBJ0.0xb798 +48010000 OBJ0.0xb79c +18011de4 OBJ0.0xb7a0 +28000000 OBJ0.0xb7a4 +1c015de4 OBJ0.0xb7a8 +28000000 OBJ0.0xb7ac +1cb1dc43 OBJ0.0xb7b0 +198e0000 OBJ0.0xb7b4 +000001e7 OBJ0.0xb7b8 +a8000000 OBJ0.0xb7bc +60001de7 OBJ0.0xb7c0 +4003fffc OBJ0.0xb7c4 +60031de4 OBJ0.0xb7c8 +28004404 OBJ0.0xb7cc +70035de4 OBJ0.0xb7d0 +28004404 OBJ0.0xb7d4 +3011dc85 OBJ0.0xb7d8 +c0000000 OBJ0.0xb7dc +80000007 OBJ0.0xb7e0 +68000004 OBJ0.0xb7e4 +20c11fa5 OBJ0.0xb7e8 +84000000 OBJ0.0xb7ec +10afdd03 OBJ0.0xb7f0 +48010000 OBJ0.0xb7f4 +14b1dc43 OBJ0.0xb7f8 +198e0000 OBJ0.0xb7fc +000001e7 OBJ0.0xb800 +a8000000 OBJ0.0xb804 +60001de4 OBJ0.0xb808 +28004404 OBJ0.0xb80c +20021c03 OBJ0.0xb810 +4801c000 OBJ0.0xb814 +00801c02 OBJ0.0xb818 +3bfc0000 OBJ0.0xb81c +73f25c43 OBJ0.0xb820 +48004404 OBJ0.0xb824 +0001dc03 OBJ0.0xb828 +190e4000 OBJ0.0xb82c +fc93dc03 OBJ0.0xb830 +190e0000 OBJ0.0xb834 +0401dc04 OBJ0.0xb838 +0c0e0000 OBJ0.0xb83c +600001e7 OBJ0.0xb840 +40000000 OBJ0.0xb844 +00811f25 OBJ0.0xb848 +54143000 OBJ0.0xb84c +00801ca5 OBJ0.0xb850 +9c000000 OBJ0.0xb854 +80001de7 OBJ0.0xb858 +40000001 OBJ0.0xb85c +60000007 OBJ0.0xb860 +60000001 OBJ0.0xb864 +00819c85 OBJ0.0xb868 +a0000000 OBJ0.0xb86c +1cf3dc04 OBJ0.0xb870 +0c0e0000 OBJ0.0xb874 +1081c185 OBJ0.0xb878 +a0000000 OBJ0.0xb87c +106fc503 OBJ0.0xb880 +48010000 OBJ0.0xb884 +1475c443 OBJ0.0xb888 +190e0000 OBJ0.0xb88c +1cb0c404 OBJ0.0xb890 +20040000 OBJ0.0xb894 +18a00404 OBJ0.0xb898 +20040000 OBJ0.0xb89c +1080c485 OBJ0.0xb8a0 +e8000000 OBJ0.0xb8a4 +00800085 OBJ0.0xb8a8 +e8000000 OBJ0.0xb8ac +c00025e7 OBJ0.0xb8b0 +4003fffe OBJ0.0xb8b4 +00001df4 OBJ0.0xb8b8 +40000000 OBJ0.0xb8bc +106fdd03 OBJ0.0xb8c0 +48010000 OBJ0.0xb8c4 +1471dc43 OBJ0.0xb8c8 +190e0000 OBJ0.0xb8cc +000001e7 OBJ0.0xb8d0 +a8000000 OBJ0.0xb8d4 +18afdd03 OBJ0.0xb8d8 +48010000 OBJ0.0xb8dc +18011de4 OBJ0.0xb8e0 +28000000 OBJ0.0xb8e4 +1c015de4 OBJ0.0xb8e8 +28000000 OBJ0.0xb8ec +1cb1dc43 OBJ0.0xb8f0 +198e0000 OBJ0.0xb8f4 +000001e7 OBJ0.0xb8f8 +a8000000 OBJ0.0xb8fc +00001de7 OBJ0.0xb900 +4003fffc OBJ0.0xb904 +40001de4 OBJ0.0xb908 +28004404 OBJ0.0xb90c +3011dc85 OBJ0.0xb910 +c0000000 OBJ0.0xb914 +60000007 OBJ0.0xb918 +60000002 OBJ0.0xb91c +20011c03 OBJ0.0xb920 +4801c000 OBJ0.0xb924 +00401c02 OBJ0.0xb928 +3bfc0000 OBJ0.0xb92c +53f15c43 OBJ0.0xb930 +48004404 OBJ0.0xb934 +0001dc03 OBJ0.0xb938 +190e4000 OBJ0.0xb93c +fc53dc03 OBJ0.0xb940 +190e0000 OBJ0.0xb944 +0401dc04 OBJ0.0xb948 +0c0e0000 OBJ0.0xb94c +600001e7 OBJ0.0xb950 +40000000 OBJ0.0xb954 +00439e05 OBJ0.0xb958 +547e3000 OBJ0.0xb95c +00401ca5 OBJ0.0xb960 +9c000000 OBJ0.0xb964 +00001de7 OBJ0.0xb968 +40000001 OBJ0.0xb96c +00419c85 OBJ0.0xb970 +a0000000 OBJ0.0xb974 +1cf3dc04 OBJ0.0xb978 +0c0e0000 OBJ0.0xb97c +1041c185 OBJ0.0xb980 +a0000000 OBJ0.0xb984 +38600403 OBJ0.0xb988 +48010000 OBJ0.0xb98c +3c70c443 OBJ0.0xb990 +48000000 OBJ0.0xb994 +00400085 OBJ0.0xb998 +e8000000 OBJ0.0xb99c +1040c485 OBJ0.0xb9a0 +e8000000 OBJ0.0xb9a4 +000025e7 OBJ0.0xb9a8 +4003ffff OBJ0.0xb9ac +00001df4 OBJ0.0xb9b0 +40000000 OBJ0.0xb9b4 +e0421fa5 OBJ0.0xb9b8 +87ffffff OBJ0.0xb9bc +38619c03 OBJ0.0xb9c0 +48010000 OBJ0.0xb9c4 +40000007 OBJ0.0xb9c8 +60000005 OBJ0.0xb9cc +3c71dc43 OBJ0.0xb9d0 +48000000 OBJ0.0xb9d4 +188fdd03 OBJ0.0xb9d8 +48010000 OBJ0.0xb9dc +1c91dc43 OBJ0.0xb9e0 +1a8e0000 OBJ0.0xb9e4 +000001f4 OBJ0.0xb9e8 +40000000 OBJ0.0xb9ec +60029de4 OBJ0.0xb9f0 +28004404 OBJ0.0xb9f4 +7002dde4 OBJ0.0xb9f8 +28004404 OBJ0.0xb9fc +30125e85 OBJ0.0xba00 +c0000000 OBJ0.0xba04 +20000007 OBJ0.0xba08 +68000004 OBJ0.0xba0c +00a11fa5 OBJ0.0xba10 +84000000 OBJ0.0xba14 +184fdd03 OBJ0.0xba18 +48010000 OBJ0.0xba1c +1c51dc43 OBJ0.0xba20 +1b0e0000 OBJ0.0xba24 +000001e7 OBJ0.0xba28 +a8000000 OBJ0.0xba2c +00c01c02 OBJ0.0xba30 +3bfc0000 OBJ0.0xba34 +fcd3dc03 OBJ0.0xba38 +190e0000 OBJ0.0xba3c +0001dc03 OBJ0.0xba40 +190e4000 OBJ0.0xba44 +0401dc04 OBJ0.0xba48 +0c0e0000 OBJ0.0xba4c +600001e7 OBJ0.0xba50 +40000000 OBJ0.0xba54 +00c11f25 OBJ0.0xba58 +540c4000 OBJ0.0xba5c +00c01ca5 OBJ0.0xba60 +9c000000 OBJ0.0xba64 +80001de7 OBJ0.0xba68 +40000001 OBJ0.0xba6c +60000007 OBJ0.0xba70 +60000001 OBJ0.0xba74 +00c21c85 OBJ0.0xba78 +a0000000 OBJ0.0xba7c +1cf3dc04 OBJ0.0xba80 +0c0e0000 OBJ0.0xba84 +10c24185 OBJ0.0xba88 +a0000000 OBJ0.0xba8c +108fc503 OBJ0.0xba90 +48010000 OBJ0.0xba94 +1495c443 OBJ0.0xba98 +190e0000 OBJ0.0xba9c +2470c404 OBJ0.0xbaa0 +20040000 OBJ0.0xbaa4 +20600404 OBJ0.0xbaa8 +20040000 OBJ0.0xbaac +10c0c485 OBJ0.0xbab0 +e8000000 OBJ0.0xbab4 +00c00085 OBJ0.0xbab8 +e8000000 OBJ0.0xbabc +c00025e7 OBJ0.0xbac0 +4003fffe OBJ0.0xbac4 +00001df4 OBJ0.0xbac8 +40000000 OBJ0.0xbacc +108fdd03 OBJ0.0xbad0 +48010000 OBJ0.0xbad4 +1491dc43 OBJ0.0xbad8 +190e0000 OBJ0.0xbadc +000001e7 OBJ0.0xbae0 +a8000000 OBJ0.0xbae4 +188fdd03 OBJ0.0xbae8 +48010000 OBJ0.0xbaec +20011de4 OBJ0.0xbaf0 +28000000 OBJ0.0xbaf4 +24015de4 OBJ0.0xbaf8 +28000000 OBJ0.0xbafc +1c91dc43 OBJ0.0xbb00 +1b0e0000 OBJ0.0xbb04 +000001e7 OBJ0.0xbb08 +a8000000 OBJ0.0xbb0c +60001de7 OBJ0.0xbb10 +4003fffc OBJ0.0xbb14 +00001df4 OBJ0.0xbb18 +40000000 OBJ0.0xbb1c +00001c05 OBJ0.0xbb20 +e0000000 OBJ0.0xbb24 +00001c45 OBJ0.0xbb28 +e0000000 OBJ0.0xbb2c +fc9fdc03 OBJ0.0xbb30 +207e0000 OBJ0.0xbb34 +00001df4 OBJ0.0xbb38 +40000000 OBJ0.0xbb3c +1010de85 OBJ0.0xbb40 +c0000000 OBJ0.0xbb44 +00101c85 OBJ0.0xbb48 +c0000002 OBJ0.0xbb4c +fc31dc03 OBJ0.0xbb50 +1a8e0000 OBJ0.0xbb54 +f8011c04 OBJ0.0xbb58 +2000ffff OBJ0.0xbb5c +40109e85 OBJ0.0xbb60 +c0000000 OBJ0.0xbb64 +80105c03 OBJ0.0xbb68 +4800c002 OBJ0.0xbb6c +00001de7 OBJ0.0xbb70 +90000000 OBJ0.0xbb74 +200446c0 OBJ0.0xbb78 +00000000 OBJ0.0xbb7c +0800ffd0 OBJ0.0xbb80 +00000060 OBJ0.0xbb84 +00000000 OBJ0.0xbb88 +# out of band: 000002f8 0810b344 +# out of band: 000002fc 001d2200 +200145a6 OBJ0.0xbb8c +00000001 OBJ0.0xbb90 +200446c0 OBJ0.0xbb94 +00000000 OBJ0.0xbb98 +0800ffd0 OBJ0.0xbb9c +00000061 OBJ0.0xbba0 +00000000 OBJ0.0xbba4 +# out of band: 00000300 0810d064 +# out of band: 00000304 00001e00 +200348e0 OBJ0.0xbba8 +00010000 OBJ0.0xbbac +00000001 OBJ0.0xbbb0 +00005400 OBJ0.0xbbb4 +200148e3 OBJ0.0xbbb8 +00000000 OBJ0.0xbbbc +602a48e4 OBJ0.0xbbc0 +20105d03 OBJ0.0xbbc4 +4800c000 OBJ0.0xbbc8 +14001de4 OBJ0.0xbbcc +28000000 OBJ0.0xbbd0 +10109c85 OBJ0.0xbbd4 +c8000000 OBJ0.0xbbd8 +00101c85 OBJ0.0xbbdc +c8000000 OBJ0.0xbbe0 +10009de4 OBJ0.0xbbe4 +28000000 OBJ0.0xbbe8 +00010007 OBJ0.0xbbec +100001c8 OBJ0.0xbbf0 +00101e85 OBJ0.0xbbf4 +c0000000 OBJ0.0xbbf8 +08011de4 OBJ0.0xbbfc +28000000 OBJ0.0xbc00 +00015de4 OBJ0.0xbc04 +28000000 OBJ0.0xbc08 +00010007 OBJ0.0xbc0c +10000214 OBJ0.0xbc10 +14001de4 OBJ0.0xbc14 +28000000 OBJ0.0xbc18 +10009de4 OBJ0.0xbc1c +28000000 OBJ0.0xbc20 +04011de2 OBJ0.0xbc24 +18000000 OBJ0.0xbc28 +00101c85 OBJ0.0xbc2c +c8000000 OBJ0.0xbc30 +00010007 OBJ0.0xbc34 +100001d4 OBJ0.0xbc38 +00101e85 OBJ0.0xbc3c +c0000000 OBJ0.0xbc40 +08011de4 OBJ0.0xbc44 +28000000 OBJ0.0xbc48 +10109e85 OBJ0.0xbc4c +c0000000 OBJ0.0xbc50 +00015de4 OBJ0.0xbc54 +28000000 OBJ0.0xbc58 +20105c03 OBJ0.0xbc5c +4800c000 OBJ0.0xbc60 +00001de7 OBJ0.0xbc64 +90000000 OBJ0.0xbc68 +200446c0 OBJ0.0xbc6c +00000000 OBJ0.0xbc70 +0800ffd0 OBJ0.0xbc74 +00000062 OBJ0.0xbc78 +00000000 OBJ0.0xbc7c +# out of band: 00000308 0810d080 +# out of band: 0000030c 0000da00 +200145a6 OBJ0.0xbc80 +00000001 OBJ0.0xbc84 +200446c0 OBJ0.0xbc88 +00000000 OBJ0.0xbc8c +0800ffd0 OBJ0.0xbc90 +00000063 OBJ0.0xbc94 +00000000 OBJ0.0xbc98 +# out of band: 00000310 0810d158 +# out of band: 00000314 00001e00 +200348e0 OBJ0.0xbc9c +00010000 OBJ0.0xbca0 +00000001 OBJ0.0xbca4 +00005300 OBJ0.0xbca8 +200148e3 OBJ0.0xbcac +00000000 OBJ0.0xbcb0 +600448e4 OBJ0.0xbcb4 +00010007 OBJ0.0xbcb8 +100002e8 OBJ0.0xbcbc +00001de7 OBJ0.0xbcc0 +90000000 OBJ0.0xbcc4 +200446c0 OBJ0.0xbcc8 +00000000 OBJ0.0xbccc +0800ffd0 OBJ0.0xbcd0 +00000064 OBJ0.0xbcd4 +00000000 OBJ0.0xbcd8 +# out of band: 00000318 0810d174 +# out of band: 0000031c 00004200 +200145a6 OBJ0.0xbcdc +00000001 OBJ0.0xbce0 +200446c0 OBJ0.0xbce4 +00000000 OBJ0.0xbce8 +0800ffd0 OBJ0.0xbcec +00000065 OBJ0.0xbcf0 +00000000 OBJ0.0xbcf4 +# out of band: 00000320 0810d1b4 +# out of band: 00000324 00001e00 +200348e0 OBJ0.0xbcf8 +00010000 OBJ0.0xbcfc +00000001 OBJ0.0xbd00 +00004e00 OBJ0.0xbd04 +200148e3 OBJ0.0xbd08 +00000000 OBJ0.0xbd0c +613648e4 OBJ0.0xbd10 +40105d03 OBJ0.0xbd14 +4800c001 OBJ0.0xbd18 +60101c03 OBJ0.0xbd1c +4800c000 OBJ0.0xbd20 +20131ca5 OBJ0.0xbd24 +c8000000 OBJ0.0xbd28 +40111c85 OBJ0.0xbd2c +c8000000 OBJ0.0xbd30 +10039c03 OBJ0.0xbd34 +48014000 OBJ0.0xbd38 +50115c85 OBJ0.0xbd3c +c8000000 OBJ0.0xbd40 +1ce01c03 OBJ0.0xbd44 +6800c000 OBJ0.0xbd48 +03f0dc04 OBJ0.0xbd4c +3000c3c0 OBJ0.0xbd50 +fc0fdd03 OBJ0.0xbd54 +48010000 OBJ0.0xbd58 +fff1dc43 OBJ0.0xbd5c +1a8e0000 OBJ0.0xbd60 +04cfdd03 OBJ0.0xbd64 +4801c000 OBJ0.0xbd68 +fcd3dc43 OBJ0.0xbd6c +1a8e0000 OBJ0.0xbd70 +00301c04 OBJ0.0xbd74 +3400c3c0 OBJ0.0xbd78 +fff3dc43 OBJ0.0xbd7c +48000000 OBJ0.0xbd80 +10e38003 OBJ0.0xbd84 +4801c000 OBJ0.0xbd88 +fcf3c043 OBJ0.0xbd8c +48000000 OBJ0.0xbd90 +20e31c03 OBJ0.0xbd94 +4801c000 OBJ0.0xbd98 +00e19fa5 OBJ0.0xbd9c +94000000 OBJ0.0xbda0 +0cc01c03 OBJ0.0xbda4 +6800c000 OBJ0.0xbda8 +fcf35c43 OBJ0.0xbdac +48000000 OBJ0.0xbdb0 +fc0fdd03 OBJ0.0xbdb4 +48010000 OBJ0.0xbdb8 +fff1dc43 OBJ0.0xbdbc +1a8e0000 OBJ0.0xbdc0 +30e30003 OBJ0.0xbdc4 +4801c000 OBJ0.0xbdc8 +fcf34043 OBJ0.0xbdcc +48000000 OBJ0.0xbdd0 +10c01c03 OBJ0.0xbdd4 +4801c000 OBJ0.0xbdd8 +00c21f85 OBJ0.0xbddc +94000000 OBJ0.0xbde0 +fcd0dc43 OBJ0.0xbde4 +48000000 OBJ0.0xbde8 +400085e7 OBJ0.0xbdec +40000001 OBJ0.0xbdf0 +1c012403 OBJ0.0xbdf4 +6800c000 OBJ0.0xbdf8 +fc4fe503 OBJ0.0xbdfc +48010000 OBJ0.0xbe00 +fff1e443 OBJ0.0xbe04 +1a8e0000 OBJ0.0xbe08 +10012403 OBJ0.0xbe0c +4801c000 OBJ0.0xbe10 +fc316443 OBJ0.0xbe14 +48000000 OBJ0.0xbe18 +00412404 OBJ0.0xbe1c +20000000 OBJ0.0xbe20 +0c516404 OBJ0.0xbe24 +20000000 OBJ0.0xbe28 +20402403 OBJ0.0xbe2c +4801c000 OBJ0.0xbe30 +0042a7a5 OBJ0.0xbe34 +94000000 OBJ0.0xbe38 +fc50e443 OBJ0.0xbe3c +48000000 OBJ0.0xbe40 +0c011c03 OBJ0.0xbe44 +6800c000 OBJ0.0xbe48 +00109c85 OBJ0.0xbe4c +c8000000 OBJ0.0xbe50 +fc4fdd03 OBJ0.0xbe54 +48010000 OBJ0.0xbe58 +fff3dc43 OBJ0.0xbe5c +1a8e0000 OBJ0.0xbe60 +10011c03 OBJ0.0xbe64 +4801c000 OBJ0.0xbe68 +00409c04 OBJ0.0xbe6c +20020000 OBJ0.0xbe70 +fc315c43 OBJ0.0xbe74 +48000000 OBJ0.0xbe78 +10211c03 OBJ0.0xbe7c +4801c000 OBJ0.0xbe80 +0c50dc04 OBJ0.0xbe84 +20020000 OBJ0.0xbe88 +0c401c03 OBJ0.0xbe8c +6800c000 OBJ0.0xbe90 +03f19c04 OBJ0.0xbe94 +3000c3c0 OBJ0.0xbe98 +fc0fdd03 OBJ0.0xbe9c +48010000 OBJ0.0xbea0 +fff1dc43 OBJ0.0xbea4 +1a8e0000 OBJ0.0xbea8 +00601c04 OBJ0.0xbeac +3400c3c0 OBJ0.0xbeb0 +fc315c43 OBJ0.0xbeb4 +48000000 OBJ0.0xbeb8 +20210003 OBJ0.0xbebc +4801c000 OBJ0.0xbec0 +fc314043 OBJ0.0xbec4 +48000000 OBJ0.0xbec8 +10429c03 OBJ0.0xbecc +4801c000 OBJ0.0xbed0 +10111c85 OBJ0.0xbed4 +c8000000 OBJ0.0xbed8 +0ca01c03 OBJ0.0xbedc +6800c000 OBJ0.0xbee0 +03f19c04 OBJ0.0xbee4 +3000c3c0 OBJ0.0xbee8 +fc0fdd03 OBJ0.0xbeec +48010000 OBJ0.0xbef0 +fff1dc43 OBJ0.0xbef4 +1a8e0000 OBJ0.0xbef8 +00601c04 OBJ0.0xbefc +3400c3c0 OBJ0.0xbf00 +fc52dc43 OBJ0.0xbf04 +48000000 OBJ0.0xbf08 +20428003 OBJ0.0xbf0c +4801c000 OBJ0.0xbf10 +fc52c043 OBJ0.0xbf14 +48000000 OBJ0.0xbf18 +10a19c03 OBJ0.0xbf1c +4801c000 OBJ0.0xbf20 +0c601c03 OBJ0.0xbf24 +6800c000 OBJ0.0xbf28 +03f11c04 OBJ0.0xbf2c +3000c3c0 OBJ0.0xbf30 +fc0fdd03 OBJ0.0xbf34 +48010000 OBJ0.0xbf38 +fff1dc43 OBJ0.0xbf3c +1a8e0000 OBJ0.0xbf40 +00401c04 OBJ0.0xbf44 +3400c3c0 OBJ0.0xbf48 +fcb1dc43 OBJ0.0xbf4c +48000000 OBJ0.0xbf50 +10618003 OBJ0.0xbf54 +4801c000 OBJ0.0xbf58 +fc71c043 OBJ0.0xbf5c +48000000 OBJ0.0xbf60 +10621c03 OBJ0.0xbf64 +4801c000 OBJ0.0xbf68 +0c801c03 OBJ0.0xbf6c +6800c000 OBJ0.0xbf70 +03f11c04 OBJ0.0xbf74 +3000c3c0 OBJ0.0xbf78 +fc0fdd03 OBJ0.0xbf7c +48010000 OBJ0.0xbf80 +fff1dc43 OBJ0.0xbf84 +1a8e0000 OBJ0.0xbf88 +00401c04 OBJ0.0xbf8c +3400c3c0 OBJ0.0xbf90 +fc725c43 OBJ0.0xbf94 +48000000 OBJ0.0xbf98 +20620003 OBJ0.0xbf9c +4801c000 OBJ0.0xbfa0 +fc724043 OBJ0.0xbfa4 +48000000 OBJ0.0xbfa8 +10831c03 OBJ0.0xbfac +4801c000 OBJ0.0xbfb0 +0cc01c03 OBJ0.0xbfb4 +6800c000 OBJ0.0xbfb8 +03f11c04 OBJ0.0xbfbc +3000c3c0 OBJ0.0xbfc0 +fc0fdd03 OBJ0.0xbfc4 +48010000 OBJ0.0xbfc8 +fff1dc43 OBJ0.0xbfcc +1a8e0000 OBJ0.0xbfd0 +00401c04 OBJ0.0xbfd4 +3400c3c0 OBJ0.0xbfd8 +94011c04 OBJ0.0xbfdc +2c000000 OBJ0.0xbfe0 +13f3dc03 OBJ0.0xbfe4 +1a8e4406 OBJ0.0xbfe8 +fc935c43 OBJ0.0xbfec +48000000 OBJ0.0xbff0 +20830003 OBJ0.0xbff4 +4801c000 OBJ0.0xbff8 +00211f85 OBJ0.0xbffc +94000000 OBJ0.0xc000 +fc934043 OBJ0.0xc004 +48000000 OBJ0.0xc008 +10c39c03 OBJ0.0xc00c +4801c000 OBJ0.0xc010 +10111e85 OBJ0.0xc014 +c0000000 OBJ0.0xc018 +9c00dc04 OBJ0.0xc01c +2c000000 OBJ0.0xc020 +1ce01c03 OBJ0.0xc024 +6800c000 OBJ0.0xc028 +fcd3dc43 OBJ0.0xc02c +48000000 OBJ0.0xc030 +00109e85 OBJ0.0xc034 +c0000000 OBJ0.0xc038 +fc0fdd03 OBJ0.0xc03c +48010000 OBJ0.0xc040 +98001c04 OBJ0.0xc044 +2c000000 OBJ0.0xc048 +fff1dc43 OBJ0.0xc04c +1a8e0000 OBJ0.0xc050 +00401f85 OBJ0.0xc054 +94000000 OBJ0.0xc058 +00a0df85 OBJ0.0xc05c +94000000 OBJ0.0xc060 +10e38003 OBJ0.0xc064 +4801c000 OBJ0.0xc068 +84001c04 OBJ0.0xc06c +2c000000 OBJ0.0xc070 +40111ea5 OBJ0.0xc074 +c0000000 OBJ0.0xc078 +8800dc04 OBJ0.0xc07c +2c000000 OBJ0.0xc080 +8c029c04 OBJ0.0xc084 +2c000000 OBJ0.0xc088 +00601f85 OBJ0.0xc08c +94000000 OBJ0.0xc090 +fcf3c043 OBJ0.0xc094 +48000000 OBJ0.0xc098 +0080df85 OBJ0.0xc09c +94000000 OBJ0.0xc0a0 +00c29f85 OBJ0.0xc0a4 +94000000 OBJ0.0xc0a8 +00e11fa5 OBJ0.0xc0ac +94000000 OBJ0.0xc0b0 +c00005e7 OBJ0.0xc0b4 +40000001 OBJ0.0xc0b8 +20101e85 OBJ0.0xc0bc +c0000000 OBJ0.0xc0c0 +3010de85 OBJ0.0xc0c4 +c0000000 OBJ0.0xc0c8 +40019de4 OBJ0.0xc0cc +28004406 OBJ0.0xc0d0 +fc01dde4 OBJ0.0xc0d4 +28000000 OBJ0.0xc0d8 +fc015de4 OBJ0.0xc0dc +28000000 OBJ0.0xc0e0 +04011de2 OBJ0.0xc0e4 +18000000 OBJ0.0xc0e8 +040fdd03 OBJ0.0xc0ec +4801c000 OBJ0.0xc0f0 +60101c03 OBJ0.0xc0f4 +4800c000 OBJ0.0xc0f8 +fc31dc43 OBJ0.0xc0fc +1a8e0000 OBJ0.0xc100 +10021c03 OBJ0.0xc104 +48014000 OBJ0.0xc108 +500181e4 OBJ0.0xc10c +28004406 OBJ0.0xc110 +fc01c1e4 OBJ0.0xc114 +28000000 OBJ0.0xc118 +fff25c43 OBJ0.0xc11c +48000000 OBJ0.0xc120 +00010007 OBJ0.0xc124 +10000154 OBJ0.0xc128 +00701c24 OBJ0.0xc12c +49c00000 OBJ0.0xc130 +0000dc04 OBJ0.0xc134 +2c000000 OBJ0.0xc138 +40000007 OBJ0.0xc13c +60000002 OBJ0.0xc140 +00001c03 OBJ0.0xc144 +78000000 OBJ0.0xc148 +7c30de03 OBJ0.0xc14c +4800c000 OBJ0.0xc150 +7c001e03 OBJ0.0xc154 +4800c000 OBJ0.0xc158 +0c01dc03 OBJ0.0xc15c +1a8e0000 OBJ0.0xc160 +800001e7 OBJ0.0xc164 +40000001 OBJ0.0xc168 +0c001c04 OBJ0.0xc16c +2c000000 OBJ0.0xc170 +0c00dc04 OBJ0.0xc174 +2c000000 OBJ0.0xc178 +20001c03 OBJ0.0xc17c +7000c018 OBJ0.0xc180 +5030dc03 OBJ0.0xc184 +7000c024 OBJ0.0xc188 +00301c03 OBJ0.0xc18c +20004406 OBJ0.0xc190 +20011c03 OBJ0.0xc194 +48014406 OBJ0.0xc198 +0c001de2 OBJ0.0xc19c +18000002 OBJ0.0xc1a0 +33f15c43 OBJ0.0xc1a4 +48004406 OBJ0.0xc1a8 +00401f05 OBJ0.0xc1ac +94000000 OBJ0.0xc1b0 +00001c05 OBJ0.0xc1b4 +e0000000 OBJ0.0xc1b8 +00001c45 OBJ0.0xc1bc +e0000000 OBJ0.0xc1c0 +fc2fdc03 OBJ0.0xc1c4 +207e0000 OBJ0.0xc1c8 +00001df4 OBJ0.0xc1cc +40000000 OBJ0.0xc1d0 +0000c007 OBJ0.0xc1d4 +d0000000 OBJ0.0xc1d8 +40105c03 OBJ0.0xc1dc +4800c001 OBJ0.0xc1e0 +00001de7 OBJ0.0xc1e4 +90000000 OBJ0.0xc1e8 +200446c0 OBJ0.0xc1ec +00000000 OBJ0.0xc1f0 +0800ffd0 OBJ0.0xc1f4 +00000066 OBJ0.0xc1f8 +00000000 OBJ0.0xc1fc +# out of band: 00000328 0810d1d0 +# out of band: 0000032c 00050a00 +200145a6 OBJ0.0xc200 +00000001 OBJ0.0xc204 +200446c0 OBJ0.0xc208 +00000000 OBJ0.0xc20c +0800ffd0 OBJ0.0xc210 +00000067 OBJ0.0xc214 +00000000 OBJ0.0xc218 +# out of band: 00000330 0810d6d8 +# out of band: 00000334 00001e00 +200348e0 OBJ0.0xc21c +00010000 OBJ0.0xc220 +00000001 OBJ0.0xc224 +00004d00 OBJ0.0xc228 +200148e3 OBJ0.0xc22c +00000000 OBJ0.0xc230 +600448e4 OBJ0.0xc234 +00010007 OBJ0.0xc238 +100002e8 OBJ0.0xc23c +00001de7 OBJ0.0xc240 +90000000 OBJ0.0xc244 +200446c0 OBJ0.0xc248 +00000000 OBJ0.0xc24c +0800ffd0 OBJ0.0xc250 +00000068 OBJ0.0xc254 +00000000 OBJ0.0xc258 +# out of band: 00000338 0810d6f4 +# out of band: 0000033c 00004200 +200145a6 OBJ0.0xc25c +00000001 OBJ0.0xc260 +200446c0 OBJ0.0xc264 +00000000 OBJ0.0xc268 +0800ffd0 OBJ0.0xc26c +00000069 OBJ0.0xc270 +00000000 OBJ0.0xc274 +# out of band: 00000340 0810d734 +# out of band: 00000344 00001e00 +200348e0 OBJ0.0xc278 +00010000 OBJ0.0xc27c +00000001 OBJ0.0xc280 +00004c00 OBJ0.0xc284 +200148e3 OBJ0.0xc288 +00000000 OBJ0.0xc28c +603e48e4 OBJ0.0xc290 +10801c03 OBJ0.0xc294 +4800c000 OBJ0.0xc298 +10019de4 OBJ0.0xc29c +28000000 OBJ0.0xc2a0 +1401dde4 OBJ0.0xc2a4 +28000000 OBJ0.0xc2a8 +f000dc03 OBJ0.0xc2ac +6800ffff OBJ0.0xc2b0 +fc31dc03 OBJ0.0xc2b4 +190e0000 OBJ0.0xc2b8 +a00001e7 OBJ0.0xc2bc +40000002 OBJ0.0xc2c0 +fc4fdd03 OBJ0.0xc2c4 +48010000 OBJ0.0xc2c8 +fc51dc43 OBJ0.0xc2cc +190e0000 OBJ0.0xc2d0 +800001e7 OBJ0.0xc2d4 +40000002 OBJ0.0xc2d8 +fc001de4 OBJ0.0xc2dc +28000000 OBJ0.0xc2e0 +fc011de4 OBJ0.0xc2e4 +28000000 OBJ0.0xc2e8 +0c615c03 OBJ0.0xc2ec +6800c000 OBJ0.0xc2f0 +fc51dc03 OBJ0.0xc2f4 +1a8e0000 OBJ0.0xc2f8 +800081e7 OBJ0.0xc2fc +40000000 OBJ0.0xc300 +00616385 OBJ0.0xc304 +84000000 OBJ0.0xc308 +c80221e2 OBJ0.0xc30c +1a965313 OBJ0.0xc310 +2053e003 OBJ0.0xc314 +190e0000 OBJ0.0xc318 +04412004 OBJ0.0xc31c +2012c000 OBJ0.0xc320 +04001c03 OBJ0.0xc324 +4800c000 OBJ0.0xc328 +04619c03 OBJ0.0xc32c +4801c000 OBJ0.0xc330 +0031dc03 OBJ0.0xc334 +198e0000 OBJ0.0xc338 +fc71dc43 OBJ0.0xc33c +48000000 OBJ0.0xc340 +e00001e7 OBJ0.0xc344 +40000000 OBJ0.0xc348 +fc6fdd03 OBJ0.0xc34c +48010000 OBJ0.0xc350 +fc71dc43 OBJ0.0xc354 +1a8e0000 OBJ0.0xc358 +200001e7 OBJ0.0xc35c +4003fffe OBJ0.0xc360 +60001de7 OBJ0.0xc364 +40000000 OBJ0.0xc368 +fc011de4 OBJ0.0xc36c +28000000 OBJ0.0xc370 +20001de7 OBJ0.0xc374 +40000000 OBJ0.0xc378 +fc011de4 OBJ0.0xc37c +28000000 OBJ0.0xc380 +00001de7 OBJ0.0xc384 +90000000 OBJ0.0xc388 +200446c0 OBJ0.0xc38c +00000000 OBJ0.0xc390 +0800ffd0 OBJ0.0xc394 +0000006a OBJ0.0xc398 +00000000 OBJ0.0xc39c +# out of band: 00000348 0810d750 +# out of band: 0000034c 00012a00 +200145a6 OBJ0.0xc3a0 +00000001 OBJ0.0xc3a4 +200446c0 OBJ0.0xc3a8 +00000000 OBJ0.0xc3ac +0800ffd0 OBJ0.0xc3b0 +0000006b OBJ0.0xc3b4 +00000000 OBJ0.0xc3b8 +# out of band: 00000350 0810d878 +# out of band: 00000354 00001e00 +200348e0 OBJ0.0xc3bc +00010000 OBJ0.0xc3c0 +00000001 OBJ0.0xc3c4 +00004b00 OBJ0.0xc3c8 +200148e3 OBJ0.0xc3cc +00000000 OBJ0.0xc3d0 +601c48e4 OBJ0.0xc3d4 +00421fa5 OBJ0.0xc3d8 +84000000 OBJ0.0xc3dc +0c801c03 OBJ0.0xc3e0 +6800c000 OBJ0.0xc3e4 +fc0fdd03 OBJ0.0xc3e8 +48010000 OBJ0.0xc3ec +fff1dc43 OBJ0.0xc3f0 +190e0000 OBJ0.0xc3f4 +600081e7 OBJ0.0xc3f8 +40000000 OBJ0.0xc3fc +10822003 OBJ0.0xc400 +4801c000 OBJ0.0xc404 +fc926043 OBJ0.0xc408 +48000000 OBJ0.0xc40c +004223a5 OBJ0.0xc410 +94000000 OBJ0.0xc414 +00819f85 OBJ0.0xc418 +94000000 OBJ0.0xc41c +00429fa5 OBJ0.0xc420 +84000000 OBJ0.0xc424 +10a19c03 OBJ0.0xc428 +4801c000 OBJ0.0xc42c +fcb1dc43 OBJ0.0xc430 +48000000 OBJ0.0xc434 +00419fa5 OBJ0.0xc438 +94000000 OBJ0.0xc43c +00001de7 OBJ0.0xc440 +90000000 OBJ0.0xc444 +200446c0 OBJ0.0xc448 +00000000 OBJ0.0xc44c +0800ffd0 OBJ0.0xc450 +0000006c OBJ0.0xc454 +00000000 OBJ0.0xc458 +# out of band: 00000358 0810d894 +# out of band: 0000035c 0000a200 +200145a6 OBJ0.0xc45c +00000001 OBJ0.0xc460 +200446c0 OBJ0.0xc464 +00000000 OBJ0.0xc468 +0800ffd0 OBJ0.0xc46c +0000006d OBJ0.0xc470 +00000000 OBJ0.0xc474 +# out of band: 00000360 0810d934 +# out of band: 00000364 00001e00 +200348e0 OBJ0.0xc478 +00010000 OBJ0.0xc47c +00000001 OBJ0.0xc480 +00004a00 OBJ0.0xc484 +200148e3 OBJ0.0xc488 +00000000 OBJ0.0xc48c +602048e4 OBJ0.0xc490 +10021de4 OBJ0.0xc494 +28000000 OBJ0.0xc498 +14025de4 OBJ0.0xc49c +28000000 OBJ0.0xc4a0 +00811fa5 OBJ0.0xc4a4 +84000000 OBJ0.0xc4a8 +1c401c03 OBJ0.0xc4ac +6800c000 OBJ0.0xc4b0 +fc0fdd03 OBJ0.0xc4b4 +48010000 OBJ0.0xc4b8 +fff1dc43 OBJ0.0xc4bc +190e0000 OBJ0.0xc4c0 +600081e7 OBJ0.0xc4c4 +40000000 OBJ0.0xc4c8 +10412003 OBJ0.0xc4cc +4801c000 OBJ0.0xc4d0 +fc516043 OBJ0.0xc4d4 +48000000 OBJ0.0xc4d8 +008123a5 OBJ0.0xc4dc +94000000 OBJ0.0xc4e0 +00419fa5 OBJ0.0xc4e4 +94000000 OBJ0.0xc4e8 +00829fa5 OBJ0.0xc4ec +84000000 OBJ0.0xc4f0 +20a11c03 OBJ0.0xc4f4 +4801c000 OBJ0.0xc4f8 +fcb15c43 OBJ0.0xc4fc +48000000 OBJ0.0xc500 +00811fa5 OBJ0.0xc504 +94000000 OBJ0.0xc508 +00001de7 OBJ0.0xc50c +90000000 OBJ0.0xc510 +200446c0 OBJ0.0xc514 +00000000 OBJ0.0xc518 +0800ffd0 OBJ0.0xc51c +0000006e OBJ0.0xc520 +00000000 OBJ0.0xc524 +# out of band: 00000368 0810d950 +# out of band: 0000036c 0000b200 +200145a6 OBJ0.0xc528 +00000001 OBJ0.0xc52c +200446c0 OBJ0.0xc530 +00000000 OBJ0.0xc534 +0800ffd0 OBJ0.0xc538 +0000006f OBJ0.0xc53c +00000000 OBJ0.0xc540 +# out of band: 00000370 0810da00 +# out of band: 00000374 00001e00 +200348e0 OBJ0.0xc544 +00010000 OBJ0.0xc548 +00000001 OBJ0.0xc54c +00004900 OBJ0.0xc550 +200148e3 OBJ0.0xc554 +00000000 OBJ0.0xc558 +600448e4 OBJ0.0xc55c +fc011de4 OBJ0.0xc560 +28000000 OBJ0.0xc564 +00001de7 OBJ0.0xc568 +90000000 OBJ0.0xc56c +200446c0 OBJ0.0xc570 +00000000 OBJ0.0xc574 +0800ffd0 OBJ0.0xc578 +00000070 OBJ0.0xc57c +00000000 OBJ0.0xc580 +# out of band: 00000378 0810da1c +# out of band: 0000037c 00004200 +200145a6 OBJ0.0xc584 +00000001 OBJ0.0xc588 +200446c0 OBJ0.0xc58c +00000000 OBJ0.0xc590 +0800ffd0 OBJ0.0xc594 +00000071 OBJ0.0xc598 +00000000 OBJ0.0xc59c +# out of band: 00000380 0810da5c +# out of band: 00000384 00001e00 +200348e0 OBJ0.0xc5a0 +00010000 OBJ0.0xc5a4 +00000001 OBJ0.0xc5a8 +00004700 OBJ0.0xc5ac +200148e3 OBJ0.0xc5b0 +00000000 OBJ0.0xc5b4 +605848e4 OBJ0.0xc5b8 +40105d03 OBJ0.0xc5bc +4800c000 OBJ0.0xc5c0 +10001de4 OBJ0.0xc5c4 +28000000 OBJ0.0xc5c8 +1400dde4 OBJ0.0xc5cc +28000000 OBJ0.0xc5d0 +00109c85 OBJ0.0xc5d4 +c8000000 OBJ0.0xc5d8 +10101c85 OBJ0.0xc5dc +c8000000 OBJ0.0xc5e0 +3010dc85 OBJ0.0xc5e4 +c8000000 OBJ0.0xc5e8 +50409c03 OBJ0.0xc5ec +4801c000 OBJ0.0xc5f0 +fc501c43 OBJ0.0xc5f4 +48000000 OBJ0.0xc5f8 +08011de4 OBJ0.0xc5fc +28000000 OBJ0.0xc600 +20101c85 OBJ0.0xc604 +c8000000 OBJ0.0xc608 +00015de4 OBJ0.0xc60c +28000000 OBJ0.0xc610 +00010007 OBJ0.0xc614 +10000150 OBJ0.0xc618 +20101c85 OBJ0.0xc61c +c0000000 OBJ0.0xc620 +fc2fdd03 OBJ0.0xc624 +48010000 OBJ0.0xc628 +fc01dc43 OBJ0.0xc62c +190e0000 OBJ0.0xc630 +a00001e7 OBJ0.0xc634 +40000001 OBJ0.0xc638 +2010de85 OBJ0.0xc63c +c0000000 OBJ0.0xc640 +08401c03 OBJ0.0xc644 +48010000 OBJ0.0xc648 +10019de4 OBJ0.0xc64c +28000000 OBJ0.0xc650 +1401dde4 OBJ0.0xc654 +28000000 OBJ0.0xc658 +00000007 OBJ0.0xc65c +60000001 OBJ0.0xc660 +0c50dc43 OBJ0.0xc664 +48000000 OBJ0.0xc668 +006fdf05 OBJ0.0xc66c +94000000 OBJ0.0xc670 +04619c03 OBJ0.0xc674 +4801c000 OBJ0.0xc678 +fc71dc43 OBJ0.0xc67c +48000000 OBJ0.0xc680 +006fdd03 OBJ0.0xc684 +48010000 OBJ0.0xc688 +0c71dc43 OBJ0.0xc68c +1a8e0000 OBJ0.0xc690 +400001e7 OBJ0.0xc694 +4003ffff OBJ0.0xc698 +00001df4 OBJ0.0xc69c +40000000 OBJ0.0xc6a0 +10101e85 OBJ0.0xc6a4 +c0000000 OBJ0.0xc6a8 +30109e85 OBJ0.0xc6ac +c0000000 OBJ0.0xc6b0 +c8021de2 OBJ0.0xc6b4 +1a965313 OBJ0.0xc6b8 +00401c03 OBJ0.0xc6bc +48010000 OBJ0.0xc6c0 +0850dc43 OBJ0.0xc6c4 +48000000 OBJ0.0xc6c8 +0c001c03 OBJ0.0xc6cc +4801c000 OBJ0.0xc6d0 +00109e85 OBJ0.0xc6d4 +c0000000 OBJ0.0xc6d8 +fc31dc43 OBJ0.0xc6dc +48000000 OBJ0.0xc6e0 +f0019c03 OBJ0.0xc6e4 +6800ffff OBJ0.0xc6e8 +40105c03 OBJ0.0xc6ec +4800c000 OBJ0.0xc6f0 +00621f85 OBJ0.0xc6f4 +94000000 OBJ0.0xc6f8 +10621f85 OBJ0.0xc6fc +94000000 OBJ0.0xc700 +20621f85 OBJ0.0xc704 +94000000 OBJ0.0xc708 +30621f85 OBJ0.0xc70c +94000000 OBJ0.0xc710 +00001de7 OBJ0.0xc714 +90000000 OBJ0.0xc718 +200446c0 OBJ0.0xc71c +00000000 OBJ0.0xc720 +0800ffd0 OBJ0.0xc724 +00000072 OBJ0.0xc728 +00000000 OBJ0.0xc72c +# out of band: 00000388 0810da78 +# out of band: 0000038c 00019200 +200145a6 OBJ0.0xc730 +00000001 OBJ0.0xc734 +200446c0 OBJ0.0xc738 +00000000 OBJ0.0xc73c +0800ffd0 OBJ0.0xc740 +00000073 OBJ0.0xc744 +00000000 OBJ0.0xc748 +# out of band: 00000390 0810dc08 +# out of band: 00000394 00001e00 +200348e0 OBJ0.0xc74c +00010000 OBJ0.0xc750 +00000001 OBJ0.0xc754 +00004600 OBJ0.0xc758 +200148e3 OBJ0.0xc75c +00000000 OBJ0.0xc760 +601048e4 OBJ0.0xc764 +18021de4 OBJ0.0xc768 +28000000 OBJ0.0xc76c +1c025de4 OBJ0.0xc770 +28000000 OBJ0.0xc774 +1401dde4 OBJ0.0xc778 +28000000 OBJ0.0xc77c +10019de4 OBJ0.0xc780 +28000000 OBJ0.0xc784 +fc015de4 OBJ0.0xc788 +28000000 OBJ0.0xc78c +fc011de4 OBJ0.0xc790 +28000000 OBJ0.0xc794 +00010007 OBJ0.0xc798 +10000154 OBJ0.0xc79c +00001de7 OBJ0.0xc7a0 +90000000 OBJ0.0xc7a4 +200446c0 OBJ0.0xc7a8 +00000000 OBJ0.0xc7ac +0800ffd0 OBJ0.0xc7b0 +00000074 OBJ0.0xc7b4 +00000000 OBJ0.0xc7b8 +# out of band: 00000398 0810dc24 +# out of band: 0000039c 00007200 +200145a6 OBJ0.0xc7bc +00000001 OBJ0.0xc7c0 +200446c0 OBJ0.0xc7c4 +00000000 OBJ0.0xc7c8 +0800ffd0 OBJ0.0xc7cc +00000075 OBJ0.0xc7d0 +00000000 OBJ0.0xc7d4 +# out of band: 000003a0 0810dc94 +# out of band: 000003a4 00001e00 +200348e0 OBJ0.0xc7d8 +00010000 OBJ0.0xc7dc +00000001 OBJ0.0xc7e0 +00004500 OBJ0.0xc7e4 +200148e3 OBJ0.0xc7e8 +00000000 OBJ0.0xc7ec +600448e4 OBJ0.0xc7f0 +00010007 OBJ0.0xc7f4 +10000150 OBJ0.0xc7f8 +00001de7 OBJ0.0xc7fc +90000000 OBJ0.0xc800 +200446c0 OBJ0.0xc804 +00000000 OBJ0.0xc808 +0800ffd0 OBJ0.0xc80c +00000076 OBJ0.0xc810 +00000000 OBJ0.0xc814 +# out of band: 000003a8 0810dcb0 +# out of band: 000003ac 00004200 +200145a6 OBJ0.0xc818 +00000001 OBJ0.0xc81c +200446c0 OBJ0.0xc820 +00000000 OBJ0.0xc824 +0800ffd0 OBJ0.0xc828 +00000077 OBJ0.0xc82c +00000000 OBJ0.0xc830 +# out of band: 000003b0 0810dcf0 +# out of band: 000003b4 00001e00 +2002608e OBJ0.0xc834 +00000000 OBJ0.0xc838 +20100000 OBJ0.0xc83c +200260c7 OBJ0.0xc840 +00000049 OBJ0.0xc844 +00000001 OBJ0.0xc848 +200160c0 OBJ0.0xc84c +00001111 OBJ0.0xc850 +601360c1 OBJ0.0xc854 +253a7325 OBJ0.0xc858 +25203a75 OBJ0.0xc85c +62203a73 OBJ0.0xc860 +6b636f6c OBJ0.0xc864 +255b203a OBJ0.0xc868 +64252c64 OBJ0.0xc86c +5d64252c OBJ0.0xc870 +6874202c OBJ0.0xc874 +64616572 OBJ0.0xc878 +255b203a OBJ0.0xc87c +64252c64 OBJ0.0xc880 +5d64252c OBJ0.0xc884 +73734120 OBJ0.0xc888 +69747265 OBJ0.0xc88c +60206e6f OBJ0.0xc890 +20607325 OBJ0.0xc894 +6c696166 OBJ0.0xc898 +0a2e6465 OBJ0.0xc89c +00000000 OBJ0.0xc8a0 +200446c0 OBJ0.0xc8a4 +00000000 OBJ0.0xc8a8 +0800ffd0 OBJ0.0xc8ac +00000078 OBJ0.0xc8b0 +00000000 OBJ0.0xc8b4 +# out of band: 000003b8 0810dd0c +# out of band: 000003bc 00008600 +2002608e OBJ0.0xc8b8 +00000000 OBJ0.0xc8bc +20100100 OBJ0.0xc8c0 +200260c7 OBJ0.0xc8c4 +00000045 OBJ0.0xc8c8 +00000001 OBJ0.0xc8cc +200160c0 OBJ0.0xc8d0 +00001111 OBJ0.0xc8d4 +601260c1 OBJ0.0xc8d8 +253a5325 OBJ0.0xc8dc +62203a75 OBJ0.0xc8e0 +6b636f6c OBJ0.0xc8e4 +255b203a OBJ0.0xc8e8 +64252c64 OBJ0.0xc8ec +5d64252c OBJ0.0xc8f0 +6874202c OBJ0.0xc8f4 +64616572 OBJ0.0xc8f8 +255b203a OBJ0.0xc8fc +64252c64 OBJ0.0xc900 +5d64252c OBJ0.0xc904 +73734120 OBJ0.0xc908 +69747265 OBJ0.0xc90c +60206e6f OBJ0.0xc910 +20605325 OBJ0.0xc914 +6c696166 OBJ0.0xc918 +0a2e6465 OBJ0.0xc91c +00000000 OBJ0.0xc920 +200446c0 OBJ0.0xc924 +00000000 OBJ0.0xc928 +0800ffd0 OBJ0.0xc92c +00000079 OBJ0.0xc930 +00000000 OBJ0.0xc934 +# out of band: 000003c0 0810dd90 +# out of band: 000003c4 00008200 +200348e0 OBJ0.0xc938 +00010000 OBJ0.0xc93c +00000001 OBJ0.0xc940 +0000bd00 OBJ0.0xc944 +200148e3 OBJ0.0xc948 +00000000 OBJ0.0xc94c +600a48e4 OBJ0.0xc950 +c3f05c85 OBJ0.0xc954 +c803fff7 OBJ0.0xc958 +c0005de2 OBJ0.0xc95c +1803fff7 OBJ0.0xc960 +00010007 OBJ0.0xc964 +10000118 OBJ0.0xc968 +c3f05c85 OBJ0.0xc96c +c003fff7 OBJ0.0xc970 +00001de7 OBJ0.0xc974 +90000000 OBJ0.0xc978 +200446c0 OBJ0.0xc97c +00000000 OBJ0.0xc980 +0800ffd0 OBJ0.0xc984 +0000007a OBJ0.0xc988 +00000000 OBJ0.0xc98c +# out of band: 000003c8 0810de10 +# out of band: 000003cc 00005a00 +200145a6 OBJ0.0xc990 +00000001 OBJ0.0xc994 +200446c0 OBJ0.0xc998 +00000000 OBJ0.0xc99c +0800ffd0 OBJ0.0xc9a0 +0000007b OBJ0.0xc9a4 +00000000 OBJ0.0xc9a8 +# out of band: 000003d0 0810de68 +# out of band: 000003d4 00001e00 +200348e0 OBJ0.0xc9ac +00010000 OBJ0.0xc9b0 +00000001 OBJ0.0xc9b4 +0000be00 OBJ0.0xc9b8 +200148e3 OBJ0.0xc9bc +00000000 OBJ0.0xc9c0 +600a48e4 OBJ0.0xc9c4 +c3f05c85 OBJ0.0xc9c8 +c803fff7 OBJ0.0xc9cc +c0005de2 OBJ0.0xc9d0 +1803fff7 OBJ0.0xc9d4 +00010007 OBJ0.0xc9d8 +10000150 OBJ0.0xc9dc +c3f05c85 OBJ0.0xc9e0 +c003fff7 OBJ0.0xc9e4 +00001de7 OBJ0.0xc9e8 +90000000 OBJ0.0xc9ec +200446c0 OBJ0.0xc9f0 +00000000 OBJ0.0xc9f4 +0800ffd0 OBJ0.0xc9f8 +0000007c OBJ0.0xc9fc +00000000 OBJ0.0xca00 +# out of band: 000003d8 0810de84 +# out of band: 000003dc 00005a00 +200145a6 OBJ0.0xca04 +00000001 OBJ0.0xca08 +200446c0 OBJ0.0xca0c +00000000 OBJ0.0xca10 +0800ffd0 OBJ0.0xca14 +0000007d OBJ0.0xca18 +00000000 OBJ0.0xca1c +# out of band: 000003e0 0810dedc +# out of band: 000003e4 00001e00 +200348e0 OBJ0.0xca20 +00010000 OBJ0.0xca24 +00000001 OBJ0.0xca28 +0000bf00 OBJ0.0xca2c +200148e3 OBJ0.0xca30 +00000000 OBJ0.0xca34 +600a48e4 OBJ0.0xca38 +c3f05c85 OBJ0.0xca3c +c803fff7 OBJ0.0xca40 +c0005de2 OBJ0.0xca44 +1803fff7 OBJ0.0xca48 +00010007 OBJ0.0xca4c +100002e8 OBJ0.0xca50 +c3f05c85 OBJ0.0xca54 +c003fff7 OBJ0.0xca58 +00001de7 OBJ0.0xca5c +90000000 OBJ0.0xca60 +200446c0 OBJ0.0xca64 +00000000 OBJ0.0xca68 +0800ffd0 OBJ0.0xca6c +0000007e OBJ0.0xca70 +00000000 OBJ0.0xca74 +# out of band: 000003e8 0810def8 +# out of band: 000003ec 00005a00 +200145a6 OBJ0.0xca78 +00000001 OBJ0.0xca7c +200446c0 OBJ0.0xca80 +00000000 OBJ0.0xca84 +0800ffd0 OBJ0.0xca88 +0000007f OBJ0.0xca8c +00000000 OBJ0.0xca90 +# out of band: 000003f0 0810df50 +# out of band: 000003f4 00001e00 +200348e0 OBJ0.0xca94 +00010000 OBJ0.0xca98 +00000001 OBJ0.0xca9c +0000c000 OBJ0.0xcaa0 +200148e3 OBJ0.0xcaa4 +00000000 OBJ0.0xcaa8 +600a48e4 OBJ0.0xcaac +c3f05c85 OBJ0.0xcab0 +c803fff7 OBJ0.0xcab4 +c0005de2 OBJ0.0xcab8 +1803fff7 OBJ0.0xcabc +00010007 OBJ0.0xcac0 +10000138 OBJ0.0xcac4 +c3f05c85 OBJ0.0xcac8 +c003fff7 OBJ0.0xcacc +00001de7 OBJ0.0xcad0 +90000000 OBJ0.0xcad4 +200446c0 OBJ0.0xcad8 +00000000 OBJ0.0xcadc +0800ffd0 OBJ0.0xcae0 +00000080 OBJ0.0xcae4 +00000000 OBJ0.0xcae8 +# out of band: 000003f8 0810df6c +# out of band: 000003fc 00005a00 +200145a6 OBJ0.0xcaec +00000001 OBJ0.0xcaf0 +200446c0 OBJ0.0xcaf4 +00000000 OBJ0.0xcaf8 +0800ffd0 OBJ0.0xcafc +00000081 OBJ0.0xcb00 +00000000 OBJ0.0xcb04 +# out of band: 00000400 0810dfc4 +# out of band: 00000404 00001e00 +200348e0 OBJ0.0xcb08 +00010000 OBJ0.0xcb0c +00000001 OBJ0.0xcb10 +0000c100 OBJ0.0xcb14 +200148e3 OBJ0.0xcb18 +00000000 OBJ0.0xcb1c +600448e4 OBJ0.0xcb20 +00005de4 OBJ0.0xcb24 +28004404 OBJ0.0xcb28 +00001de7 OBJ0.0xcb2c +80000000 OBJ0.0xcb30 +200446c0 OBJ0.0xcb34 +00000000 OBJ0.0xcb38 +0800ffd0 OBJ0.0xcb3c +00000082 OBJ0.0xcb40 +00000000 OBJ0.0xcb44 +# out of band: 00000408 0810dfe0 +# out of band: 0000040c 00004200 +200145a6 OBJ0.0xcb48 +00000001 OBJ0.0xcb4c +200446c0 OBJ0.0xcb50 +00000000 OBJ0.0xcb54 +0800ffd0 OBJ0.0xcb58 +00000083 OBJ0.0xcb5c +00000000 OBJ0.0xcb60 +# out of band: 00000410 0810e020 +# out of band: 00000414 00001e00 +20034d00 OBJ0.0xcb64 +00000000 OBJ0.0xcb68 +00000000 OBJ0.0xcb6c +0000f000 OBJ0.0xcb70 +20014144 OBJ0.0xcb74 +00419ee0 OBJ0.0xcb78 +200446c0 OBJ0.0xcb7c +00000000 OBJ0.0xcb80 +0800ffd0 OBJ0.0xcb84 +00000084 OBJ0.0xcb88 +00000000 OBJ0.0xcb8c +# out of band: 00000418 0810e03c +# out of band: 0000041c 00002e00 +20014401 OBJ0.0xcb90 +00000001 OBJ0.0xcb94 +200446c0 OBJ0.0xcb98 +00000000 OBJ0.0xcb9c +0800ffd0 OBJ0.0xcba0 +00000085 OBJ0.0xcba4 +00000000 OBJ0.0xcba8 +# out of band: 00000420 0810e068 +# out of band: 00000424 00001e00 +20034d00 OBJ0.0xcbac +00000000 OBJ0.0xcbb0 +00000080 OBJ0.0xcbb4 +00000080 OBJ0.0xcbb8 +20014144 OBJ0.0xcbbc +00419cb0 OBJ0.0xcbc0 +200446c0 OBJ0.0xcbc4 +00000000 OBJ0.0xcbc8 +0800ffd0 OBJ0.0xcbcc +00000086 OBJ0.0xcbd0 +00000000 OBJ0.0xcbd4 +# out of band: 00000428 0810e084 +# out of band: 0000042c 00002e00 +200348e0 OBJ0.0xcbd8 +00010000 OBJ0.0xcbdc +00000001 OBJ0.0xcbe0 +0000c400 OBJ0.0xcbe4 +200148e3 OBJ0.0xcbe8 +00000000 OBJ0.0xcbec +602e48e4 OBJ0.0xcbf0 +00005de4 OBJ0.0xcbf4 +28004404 OBJ0.0xcbf8 +84015c04 OBJ0.0xcbfc +2c000000 OBJ0.0xcc00 +10031de2 OBJ0.0xcc04 +18000000 OBJ0.0xcc08 +94001c04 OBJ0.0xcc0c +2c000000 OBJ0.0xcc10 +1050dce3 OBJ0.0xcc14 +5000c000 OBJ0.0xcc18 +a0509ca3 OBJ0.0xcc1c +20198000 OBJ0.0xcc20 +0c001ca3 OBJ0.0xcc24 +5000c000 OBJ0.0xcc28 +b030dc43 OBJ0.0xcc2c +48004000 OBJ0.0xcc30 +10019ce3 OBJ0.0xcc34 +5000c000 OBJ0.0xcc38 +80011ca3 OBJ0.0xcc3c +20198000 OBJ0.0xcc40 +1402dc03 OBJ0.0xcc44 +48000000 OBJ0.0xcc48 +90615c43 OBJ0.0xcc4c +48004000 OBJ0.0xcc50 +c0b31ca3 OBJ0.0xcc54 +20198000 OBJ0.0xcc58 +10225c05 OBJ0.0xcc5c +bf00000a OBJ0.0xcc60 +10221c25 OBJ0.0xcc64 +bf001807 OBJ0.0xcc68 +10219c45 OBJ0.0xcc6c +bf003000 OBJ0.0xcc70 +24a25c03 OBJ0.0xcc74 +50000000 OBJ0.0xcc78 +10b29ce3 OBJ0.0xcc7c +5000c000 OBJ0.0xcc80 +1c81dc03 OBJ0.0xcc84 +20120000 OBJ0.0xcc88 +d0a35c43 OBJ0.0xcc8c +48004000 OBJ0.0xcc90 +00601c03 OBJ0.0xcc94 +200e0000 OBJ0.0xcc98 +00c01c85 OBJ0.0xcc9c +94000000 OBJ0.0xcca0 +00001de7 OBJ0.0xcca4 +80000000 OBJ0.0xcca8 +200446c0 OBJ0.0xccac +00000000 OBJ0.0xccb0 +0800ffd0 OBJ0.0xccb4 +00000087 OBJ0.0xccb8 +00000000 OBJ0.0xccbc +# out of band: 00000430 0810e0b0 +# out of band: 00000434 0000ea00 +200145a6 OBJ0.0xccc0 +00000001 OBJ0.0xccc4 +200446c0 OBJ0.0xccc8 +00000000 OBJ0.0xcccc +0800ffd0 OBJ0.0xccd0 +00000088 OBJ0.0xccd4 +00000000 OBJ0.0xccd8 +# out of band: 00000438 0810e198 +# out of band: 0000043c 00001e00 +200348e0 OBJ0.0xccdc +00010000 OBJ0.0xcce0 +00000001 OBJ0.0xcce4 +0000c200 OBJ0.0xcce8 +200148e3 OBJ0.0xccec +00000000 OBJ0.0xccf0 +604e48e4 OBJ0.0xccf4 +00005de4 OBJ0.0xccf8 +28004404 OBJ0.0xccfc +e0009de4 OBJ0.0xcd00 +28004000 OBJ0.0xcd04 +f000dde4 OBJ0.0xcd08 +28004000 OBJ0.0xcd0c +8402dc04 OBJ0.0xcd10 +2c000000 OBJ0.0xcd14 +94001c04 OBJ0.0xcd18 +2c000000 OBJ0.0xcd1c +00229c85 OBJ0.0xcd20 +8c000000 OBJ0.0xcd24 +fca1dc03 OBJ0.0xcd28 +190e0000 OBJ0.0xcd2c +a00001e7 OBJ0.0xcd30 +40000002 OBJ0.0xcd34 +00a1dc03 OBJ0.0xcd38 +50000000 OBJ0.0xcd3c +2c025de4 OBJ0.0xcd40 +28000000 OBJ0.0xcd44 +fc001de4 OBJ0.0xcd48 +28000000 OBJ0.0xcd4c +1c019de4 OBJ0.0xcd50 +28000000 OBJ0.0xcd54 +28721c03 OBJ0.0xcd58 +48000000 OBJ0.0xcd5c +40000007 OBJ0.0xcd60 +60000002 OBJ0.0xcd64 +10011de2 OBJ0.0xcd68 +18000000 OBJ0.0xcd6c +1090dc43 OBJ0.0xcd70 +5000c000 OBJ0.0xcd74 +10715c43 OBJ0.0xcd78 +5000c000 OBJ0.0xcd7c +a0909c03 OBJ0.0xcd80 +20098000 OBJ0.0xcd84 +28925c03 OBJ0.0xcd88 +48000000 OBJ0.0xcd8c +b030dc43 OBJ0.0xcd90 +48004000 OBJ0.0xcd94 +80711c03 OBJ0.0xcd98 +20098000 OBJ0.0xcd9c +0471dc03 OBJ0.0xcda0 +4800c000 OBJ0.0xcda4 +00209c85 OBJ0.0xcda8 +84000000 OBJ0.0xcdac +90515c43 OBJ0.0xcdb0 +48004000 OBJ0.0xcdb4 +2071dc03 OBJ0.0xcdb8 +1a8e0000 OBJ0.0xcdbc +00411c85 OBJ0.0xcdc0 +84000000 OBJ0.0xcdc4 +10201c03 OBJ0.0xcdc8 +20000000 OBJ0.0xcdcc +400001e7 OBJ0.0xcdd0 +4003fffe OBJ0.0xcdd4 +00001df4 OBJ0.0xcdd8 +40000000 OBJ0.0xcddc +00a19c03 OBJ0.0xcde0 +50000000 OBJ0.0xcde4 +fc001de4 OBJ0.0xcde8 +28000000 OBJ0.0xcdec +00001de7 OBJ0.0xcdf0 +40000000 OBJ0.0xcdf4 +2c609c03 OBJ0.0xcdf8 +48000000 OBJ0.0xcdfc +c000dde4 OBJ0.0xce00 +28004000 OBJ0.0xce04 +10211ca3 OBJ0.0xce08 +2007c000 OBJ0.0xce0c +10209ce3 OBJ0.0xce10 +5000c000 OBJ0.0xce14 +d0215c43 OBJ0.0xce18 +48004000 OBJ0.0xce1c +00401c85 OBJ0.0xce20 +94000000 OBJ0.0xce24 +00001de7 OBJ0.0xce28 +80000000 OBJ0.0xce2c +200446c0 OBJ0.0xce30 +00000000 OBJ0.0xce34 +0800ffd0 OBJ0.0xce38 +00000089 OBJ0.0xce3c +00000000 OBJ0.0xce40 +# out of band: 00000440 0810e1b4 +# out of band: 00000444 00016a00 +200145a6 OBJ0.0xce44 +00000001 OBJ0.0xce48 +200446c0 OBJ0.0xce4c +00000000 OBJ0.0xce50 +0800ffd0 OBJ0.0xce54 +0000008a OBJ0.0xce58 +00000000 OBJ0.0xce5c +# out of band: 00000448 0810e31c +# out of band: 0000044c 00001e00 +200348e0 OBJ0.0xce60 +00010000 OBJ0.0xce64 +00000000 OBJ0.0xce68 +20100200 OBJ0.0xce6c +200148e3 OBJ0.0xce70 +00000000 OBJ0.0xce74 +600148e4 OBJ0.0xce78 +00000001 OBJ0.0xce7c +200446c0 OBJ0.0xce80 +00000000 OBJ0.0xce84 +0800ffd0 OBJ0.0xce88 +0000008b OBJ0.0xce8c +00000000 OBJ0.0xce90 +# out of band: 00000450 0810e338 +# out of band: 00000454 00003600 +200348e0 OBJ0.0xce94 +00010000 OBJ0.0xce98 +00000008 OBJ0.0xce9c +00200000 OBJ0.0xcea0 +200148e3 OBJ0.0xcea4 +00000000 OBJ0.0xcea8 +600948e4 OBJ0.0xceac +00000000 OBJ0.0xceb0 +00000001 OBJ0.0xceb4 +00000002 OBJ0.0xceb8 +00000003 OBJ0.0xcebc +00000004 OBJ0.0xcec0 +00000005 OBJ0.0xcec4 +00000006 OBJ0.0xcec8 +00000007 OBJ0.0xcecc +00000008 OBJ0.0xced0 +200446c0 OBJ0.0xced4 +00000000 OBJ0.0xced8 +0800ffd0 OBJ0.0xcedc +0000008c OBJ0.0xcee0 +00000000 OBJ0.0xcee4 +# out of band: 00000458 0810e36c +# out of band: 0000045c 00005600 +200348e0 OBJ0.0xcee8 +00010000 OBJ0.0xceec +00000008 OBJ0.0xcef0 +00200200 OBJ0.0xcef4 +200148e3 OBJ0.0xcef8 +00000000 OBJ0.0xcefc +600948e4 OBJ0.0xcf00 +00000002 OBJ0.0xcf04 +00000000 OBJ0.0xcf08 +00000000 OBJ0.0xcf0c +00000000 OBJ0.0xcf10 +00000002 OBJ0.0xcf14 +00000000 OBJ0.0xcf18 +00000000 OBJ0.0xcf1c +00000000 OBJ0.0xcf20 +00000002 OBJ0.0xcf24 +200446c0 OBJ0.0xcf28 +00000000 OBJ0.0xcf2c +0800ffd0 OBJ0.0xcf30 +0000008d OBJ0.0xcf34 +00000000 OBJ0.0xcf38 +# out of band: 00000460 0810e3c0 +# out of band: 00000464 00005600 +200348e0 OBJ0.0xcf3c +00010000 OBJ0.0xcf40 +00000008 OBJ0.0xcf44 +00200400 OBJ0.0xcf48 +200148e3 OBJ0.0xcf4c +00000000 OBJ0.0xcf50 +600948e4 OBJ0.0xcf54 +000000ff OBJ0.0xcf58 +000000ff OBJ0.0xcf5c +000000ff OBJ0.0xcf60 +000000ff OBJ0.0xcf64 +000000ff OBJ0.0xcf68 +000000ff OBJ0.0xcf6c +000000ff OBJ0.0xcf70 +000000ff OBJ0.0xcf74 +000000ff OBJ0.0xcf78 +200446c0 OBJ0.0xcf7c +00000000 OBJ0.0xcf80 +0800ffd0 OBJ0.0xcf84 +0000008e OBJ0.0xcf88 +00000000 OBJ0.0xcf8c +# out of band: 00000468 0810e414 +# out of band: 0000046c 00005600 +200348e0 OBJ0.0xcf90 +00010000 OBJ0.0xcf94 +00000008 OBJ0.0xcf98 +00200600 OBJ0.0xcf9c +200148e3 OBJ0.0xcfa0 +00000000 OBJ0.0xcfa4 +600148e4 OBJ0.0xcfa8 +00000003 OBJ0.0xcfac +200446c0 OBJ0.0xcfb0 +00000000 OBJ0.0xcfb4 +0800ffd0 OBJ0.0xcfb8 +0000008f OBJ0.0xcfbc +00000000 OBJ0.0xcfc0 +# out of band: 00000470 0810e468 +# out of band: 00000474 00003600 +20014582 OBJ0.0xcfc4 +00000001 OBJ0.0xcfc8 +20014583 OBJ0.0xcfcc +00000000 OBJ0.0xcfd0 +200141e4 OBJ0.0xcfd4 +00000000 OBJ0.0xcfd8 +200141e5 OBJ0.0xcfdc +10000000 OBJ0.0xcfe0 +200141e6 OBJ0.0xcfe4 +00000000 OBJ0.0xcfe8 +200141e7 OBJ0.0xcfec +01700000 OBJ0.0xcff0 +200141e8 OBJ0.0xcff4 +00011800 OBJ0.0xcff8 +200141df OBJ0.0xcffc +03000000 OBJ0.0xd000 +20014081 OBJ0.0xd004 +000000f0 OBJ0.0xd008 +20014082 OBJ0.0xd00c +00000750 OBJ0.0xd010 +20014083 OBJ0.0xd014 +00001000 OBJ0.0xd018 +200148e0 OBJ0.0xd01c +00000100 OBJ0.0xd020 +200148e1 OBJ0.0xd024 +00000008 OBJ0.0xd028 +200148e2 OBJ0.0xd02c +000b0500 OBJ0.0xd030 +200145a5 OBJ0.0xd034 +00000001 OBJ0.0xd038 +200148e3 OBJ0.0xd03c +00000000 OBJ0.0xd040 +600848e4 OBJ0.0xd044 +01000000 OBJ0.0xd048 +03000000 OBJ0.0xd04c +00000003 OBJ0.0xd050 +00000001 OBJ0.0xd054 +00000001 OBJ0.0xd058 +00000003 OBJ0.0xd05c +00000001 OBJ0.0xd060 +00000001 OBJ0.0xd064 +600848e4 OBJ0.0xd068 +00200000 OBJ0.0xd06c +00000008 OBJ0.0xd070 +00200200 OBJ0.0xd074 +00000008 OBJ0.0xd078 +00200400 OBJ0.0xd07c +00000008 OBJ0.0xd080 +00200600 OBJ0.0xd084 +00000008 OBJ0.0xd088 +200148e0 OBJ0.0xd08c +00010000 OBJ0.0xd090 +200148e1 OBJ0.0xd094 +00000008 OBJ0.0xd098 +200148e2 OBJ0.0xd09c +000b1700 OBJ0.0xd0a0 +200145a5 OBJ0.0xd0a4 +00000101 OBJ0.0xd0a8 +200148e3 OBJ0.0xd0ac +00000000 OBJ0.0xd0b0 +602048e4 OBJ0.0xd0b4 +00000000 OBJ0.0xd0b8 +00000000 OBJ0.0xd0bc +00000000 OBJ0.0xd0c0 +00000000 OBJ0.0xd0c4 +00000000 OBJ0.0xd0c8 +00000000 OBJ0.0xd0cc +00000000 OBJ0.0xd0d0 +00000000 OBJ0.0xd0d4 +00000000 OBJ0.0xd0d8 +00000000 OBJ0.0xd0dc +00000000 OBJ0.0xd0e0 +00000000 OBJ0.0xd0e4 +00000000 OBJ0.0xd0e8 +00000000 OBJ0.0xd0ec +00000000 OBJ0.0xd0f0 +00000000 OBJ0.0xd0f4 +00000000 OBJ0.0xd0f8 +00000000 OBJ0.0xd0fc +00000000 OBJ0.0xd100 +00000000 OBJ0.0xd104 +00000000 OBJ0.0xd108 +00000000 OBJ0.0xd10c +00000000 OBJ0.0xd110 +00000000 OBJ0.0xd114 +00000000 OBJ0.0xd118 +00000000 OBJ0.0xd11c +00000000 OBJ0.0xd120 +00000000 OBJ0.0xd124 +00000000 OBJ0.0xd128 +00000000 OBJ0.0xd12c +00000000 OBJ0.0xd130 +00000000 OBJ0.0xd134 +200148e3 OBJ0.0xd138 +00000100 OBJ0.0xd13c +600148e4 OBJ0.0xd140 +00fffcb0 OBJ0.0xd144 +200148e0 OBJ0.0xd148 +00000100 OBJ0.0xd14c +200148e1 OBJ0.0xd150 +00000008 OBJ0.0xd154 +200148e2 OBJ0.0xd158 +000c1700 OBJ0.0xd15c +200145a5 OBJ0.0xd160 +00001101 OBJ0.0xd164 +200145a6 OBJ0.0xd168 +00001000 OBJ0.0xd16c +2001408e OBJ0.0xd170 +00010003 OBJ0.0xd174 +2001408f OBJ0.0xd178 +00000001 OBJ0.0xd17c +200140eb OBJ0.0xd180 +00010003 OBJ0.0xd184 +200140ec OBJ0.0xd188 +00000001 OBJ0.0xd18c +200140ed OBJ0.0xd190 +0000c200 OBJ0.0xd194 +20014094 OBJ0.0xd198 +00000003 OBJ0.0xd19c +20014095 OBJ0.0xd1a0 +00000000 OBJ0.0xd1a4 +200140b0 OBJ0.0xd1a8 +0000000c OBJ0.0xd1ac +20014093 OBJ0.0xd1b0 +00000080 OBJ0.0xd1b4 +200141e0 OBJ0.0xd1b8 +00000001 OBJ0.0xd1bc +200140db OBJ0.0xd1c0 +00000000 OBJ0.0xd1c4 +200145a6 OBJ0.0xd1c8 +00000110 OBJ0.0xd1cc +200140a7 OBJ0.0xd1d0 +00000000 OBJ0.0xd1d4 +20014282 OBJ0.0xd1d8 +00000000 OBJ0.0xd1dc +200140da OBJ0.0xd1e0 +00001000 OBJ0.0xd1e4 +20014281 OBJ0.0xd1e8 +00000000 OBJ0.0xd1ec +200140d8 OBJ0.0xd1f0 +00000001 OBJ0.0xd1f4 +200446c0 OBJ0.0xd1f8 +00000000 OBJ0.0xd1fc +0800ffd0 OBJ0.0xd200 +00000090 OBJ0.0xd204 +00000000 OBJ0.0xd208 +# out of band: 00000478 0810e49c +# out of band: 0000047c 00024a00 +200260c5 OBJ0.0xd20c +00100000 OBJ0.0xd210 +00100000 OBJ0.0xd214 +200260c3 OBJ0.0xd218 +00000008 OBJ0.0xd21c +00200000 OBJ0.0xd220 +2002608e OBJ0.0xd224 +00000000 OBJ0.0xd228 +08ba0000 OBJ0.0xd22c +200260c7 OBJ0.0xd230 +00000024 OBJ0.0xd234 +00000001 OBJ0.0xd238 +200160c0 OBJ0.0xd23c +00001110 OBJ0.0xd240 +200446c0 OBJ0.0xd244 +00000000 OBJ0.0xd248 +0800ffd0 OBJ0.0xd24c +00000091 OBJ0.0xd250 +00000000 OBJ0.0xd254 +# out of band: 00000480 0810e6e4 +# out of band: 00000484 00004e00 +200260c5 OBJ0.0xd258 +00100000 OBJ0.0xd25c +00100000 OBJ0.0xd260 +200260c3 OBJ0.0xd264 +00000008 OBJ0.0xd268 +00200200 OBJ0.0xd26c +2002608e OBJ0.0xd270 +00000000 OBJ0.0xd274 +089a0000 OBJ0.0xd278 +200260c7 OBJ0.0xd27c +00000024 OBJ0.0xd280 +00000001 OBJ0.0xd284 +200160c0 OBJ0.0xd288 +00001110 OBJ0.0xd28c +200446c0 OBJ0.0xd290 +00000000 OBJ0.0xd294 +0800ffd0 OBJ0.0xd298 +00000092 OBJ0.0xd29c +00000000 OBJ0.0xd2a0 +# out of band: 00000488 0810e730 +# out of band: 0000048c 00004e00 +200260c5 OBJ0.0xd2a4 +00100000 OBJ0.0xd2a8 +00100000 OBJ0.0xd2ac +200260c3 OBJ0.0xd2b0 +00000008 OBJ0.0xd2b4 +00200400 OBJ0.0xd2b8 +2002608e OBJ0.0xd2bc +00000000 OBJ0.0xd2c0 +08ba0000 OBJ0.0xd2c4 +200260c7 OBJ0.0xd2c8 +00000024 OBJ0.0xd2cc +00000001 OBJ0.0xd2d0 +200160c0 OBJ0.0xd2d4 +00001110 OBJ0.0xd2d8 +200446c0 OBJ0.0xd2dc +00000000 OBJ0.0xd2e0 +0800ffd0 OBJ0.0xd2e4 +00000093 OBJ0.0xd2e8 +00000000 OBJ0.0xd2ec +0810e77c OBJ0.0xd2f0 +00004e00 OBJ0.0xd2f4